Merge remote branch 'origin/master' into newnet

master
Cyp 2010-03-07 11:00:10 +01:00
commit 48533d7037
30 changed files with 967 additions and 167 deletions

View File

@ -314,8 +314,7 @@ fi
# check for nearbyint()
AC_CHECK_LIB(m, nearbyint, [MATH_LIB=""], AC_MSG_ERROR([nearbyint not found.]))
# When (cross-)compiling for Windows (MinGW) we need to link in iberty for Popt
# and the Dr. MinGW derived exception handler.
# When (cross-)compiling for Windows (MinGW) we need to link in iberty for the Dr. MinGW derived exception handler.
if test "x$host_os_mingw32" = "xyes" ; then
AC_CHECK_LIB(iberty, main, AC_SUBST([IBERTY_LIBS], [-liberty]), AC_MSG_ERROR([libiberty not found.]))
@ -334,10 +333,6 @@ AC_TRY_COMPILE(, [
AC_MSG_ERROR([X11 library not found]))
])
# Look for Popt
AC_CHECK_HEADER(popt.h, , AC_MSG_ERROR([Popt header not found.]))
AC_CHECK_LIB(popt, poptGetContext, AC_SUBST([POPT_LIBS], [-lpopt]), AC_MSG_ERROR([Popt not found.]), [${WIN32_LIBS}])
# Look for PhysicsFS
AC_CHECK_HEADER(physfs.h, , AC_MSG_ERROR([PhysicsFS header not found.]))
AC_CHECK_LIB(physfs, PHYSFS_init, AC_SUBST([PHYSFS_LIBS], [-lphysfs]), AC_MSG_ERROR([PhysicsFS not found.]), [${WIN32_LIBS}])

View File

@ -23,6 +23,7 @@ BASELIST = \
multiplay \
script \
sequenceaudio \
shaders\
stats \
structs \
tagdefinitions \

View File

@ -49,3 +49,11 @@ ff,50,50,ff // blueprint invalid
a0,a0,0,ff // health medium shadow
a0,0,0,ff // health low shadow
80,c0,ff,ff // health resistance
00,60,00,ff // team1 - green
A0,70,00,ff // team2 - orange
80,80,80,ff // team3 - gray
20,20,20,ff // team4 - black
80,00,00,ff // team5 - red
20,30,60,ff // team6 - blue
90,00,70,ff // team7 - purple
00,80,80,ff // team8 - teal

View File

@ -0,0 +1,25 @@
#pragma debug(on)
varying float vertexDistance;
uniform sampler2D Texture0;
uniform sampler2D Texture1;
uniform vec4 teamcolour;
void main(void)
{
vec4 colour, mask;
// Get color and tcmask information from TIUs 0-1
colour = texture2D(Texture0, gl_TexCoord[0].st);
mask = texture2D(Texture1, gl_TexCoord[0].st);
// Apply color using "Merge grain" within tcmask
colour = (colour + (teamcolour - 0.5) * mask.a) * gl_Color;
// Calculate linear fog
float fogFactor = (gl_Fog.end - vertexDistance) / (gl_Fog.end - gl_Fog.start);
fogFactor = clamp(fogFactor, 0.0, 1.0);
// Return fragment color
gl_FragColor = mix(gl_Fog.color, colour, fogFactor);
}

View File

@ -0,0 +1,20 @@
#pragma debug(on)
varying float vertexDistance;
void main(void)
{
// Pass vertex color information to fragment shader
gl_FrontColor = gl_Color;
// Pass texture coordinates to fragment shader
gl_TexCoord[0] = gl_TextureMatrix [0] * gl_MultiTexCoord0;
// Translate every vertex according to the Model View and Projection Matrix
//gl_Position = gl_ProjectionMatrix * gl_ModelViewMatrix * gl_Vertex;
// Use "magic" fixed routine while using GLSL < 1.30
gl_Position = ftransform();
// Remember vertex distance
vertexDistance = gl_Position.z;
}

View File

@ -20,6 +20,7 @@ BASELIST= \
palette.txt \
script \
sequenceaudio \
shaders\
stats \
structs \
tagdefinitions \

View File

@ -48,7 +48,7 @@ static unsigned short LoadTextureFile(const char *FileName)
}
debug(LOG_TEXTURE, "LoadTextureFile: had to upload texture!");
return pie_AddTexPage(pSprite, FileName, 0, 0);
return pie_AddTexPage(pSprite, FileName, 0, 0, true);
}
IMAGEFILE *iV_LoadImageFile(const char *fileName)

View File

@ -35,6 +35,9 @@
//*************************************************************************
// PIE model flags
#define iV_IMD_TCMASK 0x00010000
// polygon flags b0..b7: col, b24..b31: anim index

View File

@ -515,6 +515,7 @@ static iIMDShape *_imd_load_level(const char **ppFileData, const char *FileDataE
return NULL;
}
s->flags = 0;
s->nconnectors = 0; // Default number of connectors must be 0
s->npoints = 0;
s->npolys = 0;
@ -527,6 +528,7 @@ static iIMDShape *_imd_load_level(const char **ppFileData, const char *FileDataE
s->shadowEdgeList = NULL;
s->nShadowEdges = 0;
s->texpage = iV_TEX_INVALID;
s->tcmaskpage = iV_TEX_INVALID;
if (sscanf(pFileData, "%s %d%n", buffer, &s->npoints, &cnt) != 2)
@ -620,7 +622,7 @@ iIMDShape *iV_ProcessIMD( const char **ppFileData, const char *FileDataEnd )
iIMDShape *shape, *psShape;
UDWORD level;
int32_t imd_version;
uint32_t imd_flags; // FIXME UNUSED
uint32_t imd_flags;
BOOL bTextured = false;
if (sscanf(pFileData, "%s %d%n", buffer, &imd_version, &cnt) != 2)
@ -753,6 +755,27 @@ iIMDShape *iV_ProcessIMD( const char **ppFileData, const char *FileDataEnd )
{
psShape->texpage = texpage;
}
// check if model should use team colour mask
if (imd_flags & iV_IMD_TCMASK)
{
pie_MakeTexPageTCMaskName(texfile);
texpage = iV_GetTexture(texfile);
if (texpage < 0)
{
ASSERT(false, "iV_ProcessIMD %s could not load tcmask %s", pFileName, texfile);
debug(LOG_ERROR, "iV_ProcessIMD %s could not load tcmask %s", pFileName, texfile);
}
else
{
shape->flags |= iV_IMD_TCMASK;
for (psShape = shape; psShape != NULL; psShape = psShape->next)
{
psShape->tcmaskpage = texpage;
}
}
}
}
*ppFileData = pFileData;

View File

@ -84,7 +84,9 @@ typedef struct {
} iIMDPoly;
typedef struct _iIMDShape {
unsigned int flags;
int texpage;
int tcmaskpage;
int sradius, radius;
Vector3f min, max;

View File

@ -93,19 +93,20 @@ typedef struct {SDWORD texPage; SWORD tu, tv, tw, th;} PIEIMAGE; /**< An area of
* Global ProtoTypes
*/
/***************************************************************************/
extern void pie_Draw3DShape(iIMDShape *shape, int frame, int team, PIELIGHT colour, PIELIGHT specular, int pieFlag, int pieData);
extern void pie_Draw3DShape(iIMDShape *shape, int frame, int team, PIELIGHT colour, PIELIGHT specular, int pieFlag, int pieFlagData);
extern void pie_DrawImage(const PIEIMAGE *image, const PIERECT *dest);
extern void pie_GetResetCounts(unsigned int* pPieCount, unsigned int* pTileCount, unsigned int* pPolyCount, unsigned int* pStateCount);
/** Setup stencil shadows and OpenGL lighting. */
void pie_BeginLighting(const Vector3f * light);
void pie_BeginLighting(const Vector3f * light, bool drawshadows);
/* Stop using stencil shadows and OpenGL lighting (if enabled). */
void pie_EndLighting(void);
void pie_RemainingPasses(void);
void pie_CleanUp( void );
void pie_SetUp(void);
void pie_CleanUp(void);
#endif // _piedef_h

View File

@ -63,7 +63,7 @@
#define WZCOL_CONS_TEXT_DEBUG psPalette[38]
#define WZCOL_GREY psPalette[39]
#define WZCOL_MAP_PREVIEW_AIPLAYER psPalette[40]
#define WZCOL_MENU_SHADOW psPalette[41]
#define WZCOL_MENU_SHADOW psPalette[41]
#define WZCOL_DBLUE psPalette[42]
#define WZCOL_LBLUE psPalette[43]
#define WZCOL_BLUEPRINT_VALID psPalette[44]
@ -73,8 +73,16 @@
#define WZCOL_HEALTH_MEDIUM_SHADOW psPalette[48]
#define WZCOL_HEALTH_LOW_SHADOW psPalette[49]
#define WZCOL_HEALTH_RESISTANCE psPalette[50]
#define WZCOL_TEAM1 psPalette[51]
#define WZCOL_TEAM2 psPalette[52]
#define WZCOL_TEAM3 psPalette[53]
#define WZCOL_TEAM4 psPalette[54]
#define WZCOL_TEAM5 psPalette[55]
#define WZCOL_TEAM6 psPalette[56]
#define WZCOL_TEAM7 psPalette[57]
#define WZCOL_TEAM8 psPalette[58]
#define WZCOL_MAX 51
#define WZCOL_MAX 59
//*************************************************************************
@ -84,6 +92,7 @@ extern PIELIGHT psPalette[];
extern void pal_Init(void);
extern void pal_ShutDown(void);
extern PIELIGHT pal_GetTeamColour(int team);
static inline PIELIGHT pal_Colour(UBYTE r, UBYTE g, UBYTE b)
{
@ -122,4 +131,13 @@ static inline PIELIGHT pal_RGBA(UBYTE r, UBYTE g, UBYTE b, UBYTE a)
return c;
}
static inline void pal_PIELIGHTtoRGBA4f(float *rgba4f, PIELIGHT rgba)
{
rgba4f[0] = rgba.byte.r / 255.0;
rgba4f[1] = rgba.byte.g / 255.0;
rgba4f[2] = rgba.byte.b / 255.0;
rgba4f[3] = rgba.byte.a / 255.0;
}
#endif

View File

@ -87,6 +87,13 @@ typedef enum
TEXPAGE_FONT = -2
} TEXPAGE_TYPE;
typedef enum
{
SHADER_NONE,
SHADER_TCMASK,
SHADER_MAX
} SHADER_MODE;
/***************************************************************************/
/*
* Global Variables
@ -125,6 +132,23 @@ extern void pie_ShowMouse(bool visible);
extern void pie_SetTranslucencyMode(TRANSLUCENCY_MODE transMode);
/* Actually in piestate.c */
// Shaders control center
extern bool pie_GetShadersStatus(void);
extern void pie_SetShadersStatus(bool);
bool pie_LoadShaders(void);
// Actual shaders (we do not want to export these calls)
void pie_DeactivateShader(void);
void pie_ActivateShader_TCMask(PIELIGHT teamcolour, SDWORD maskpage);
/* Actually in piedraw.c */
// Lighting cotrols
extern void pie_SetLightingState(bool);
extern bool pie_GetLightingState(void);
/* Errors control routine */
#define glErrors() \
_glerrors(__FUNCTION__, __FILE__, __LINE__)

View File

@ -33,6 +33,8 @@
#define iV_TEX_INVALID -1
#define iV_TEXNAME_MAX 64
#define iV_TEXNAME_TCSUFFIX "_tcmask"
//*************************************************************************
#define iV_TEXNAME(i) ((char *) (&_TEX_PAGE[(i)].name))
@ -56,13 +58,14 @@ extern int iV_GetTexture(const char *filename);
extern void iV_unloadImage(iV_Image *image);
extern unsigned int iV_getPixelFormat(const iV_Image *image);
extern int pie_ReplaceTexPage(iV_Image *s, const char *texPage, int maxTextureSize);
extern int pie_AddTexPage(iV_Image *s, const char *filename, int slot, int maxTextureSize);
extern int pie_ReplaceTexPage(iV_Image *s, const char *texPage, int maxTextureSize, bool useMipmaping);
extern int pie_AddTexPage(iV_Image *s, const char *filename, int slot, int maxTextureSize, bool useMipmaping);
extern void pie_TexInit(void);
extern void pie_InitSkybox(SDWORD pageNum);
extern void pie_MakeTexPageName(char * filename);
extern void pie_MakeTexPageTCMaskName(char * filename);
//*************************************************************************

View File

@ -32,6 +32,7 @@
#include "lib/ivis_common/tex.h"
#include "lib/ivis_common/piedef.h"
#include "lib/ivis_common/piestate.h"
#include "lib/ivis_common/piepalette.h"
#include "lib/ivis_common/pieclip.h"
#include "piematrix.h"
#include "screen.h"
@ -54,14 +55,15 @@ extern BOOL drawing_interface;
static unsigned int pieCount = 0;
static unsigned int tileCount = 0;
static unsigned int polyCount = 0;
static BOOL lighting = false;
static BOOL shadows = false;
static bool lighting = false;
static bool lightingstate = false;
static bool shadows = false;
/*
* Source
*/
void pie_BeginLighting(const Vector3f * light)
void pie_BeginLighting(const Vector3f * light, bool drawshadows)
{
const float pos[4] = {light->x, light->y, light->z, 0.0f};
const float zero[4] = {0.0f, 0.0f, 0.0f, 0.0f};
@ -77,8 +79,21 @@ void pie_BeginLighting(const Vector3f * light)
glLightfv(GL_LIGHT0, GL_SPECULAR, specular);
glEnable(GL_LIGHT0);
// lighting = true;
shadows = true;
lighting = lightingstate;
if (drawshadows)
{
shadows = true;
}
}
bool pie_GetLightingState(void)
{
return lightingstate;
}
void pie_SetLightingState(bool val)
{
lightingstate = val;
}
void pie_EndLighting(void)
@ -120,10 +135,10 @@ static transluscent_shape_t* tshapes = NULL;
static unsigned int tshapes_size = 0;
static unsigned int nb_tshapes = 0;
static void pie_Draw3DShape2(iIMDShape *shape, int frame, PIELIGHT colour, WZ_DECL_UNUSED PIELIGHT specular, int pieFlag, int pieFlagData)
static void pie_Draw3DShape2(iIMDShape *shape, int frame, PIELIGHT colour, PIELIGHT teamcolour, WZ_DECL_UNUSED PIELIGHT specular, int pieFlag, int pieFlagData)
{
iIMDPoly *pPolys;
BOOL light = lighting;
bool light = lighting;
pie_SetAlphaTest(true);
@ -172,8 +187,6 @@ static void pie_Draw3DShape2(iIMDShape *shape, int frame, PIELIGHT colour, WZ_DE
glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, shininess);
}
pie_SetTexturePage(shape->texpage);
if (pieFlag & pie_HEIGHT_SCALED) // construct
{
glScalef(1.0f, (float)pieFlagData / (float)pie_RAISE_SCALE, 1.0f);
@ -184,6 +197,72 @@ static void pie_Draw3DShape2(iIMDShape *shape, int frame, PIELIGHT colour, WZ_DE
}
glColor4ubv(colour.vector); // Only need to set once for entire model
pie_SetTexturePage(shape->texpage);
// Activate TCMask if needed
if (shape->flags & iV_IMD_TCMASK && rendStates.rendMode == REND_OPAQUE)
{
#ifdef _DEBUG
glErrors();
#endif
if (pie_GetShadersStatus())
{
pie_ActivateShader_TCMask(teamcolour, shape->tcmaskpage);
}
else
{
//Set the environment colour with tcmask
GLfloat tc_env_colour[4];
pal_PIELIGHTtoRGBA4f(&tc_env_colour[0], teamcolour);
// TU0
glActiveTexture(GL_TEXTURE0);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, tc_env_colour);
// TU0 RGB
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_ADD_SIGNED);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB, GL_CONSTANT);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB, GL_SRC_COLOR);
// TU0 Alpha
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
// TU1
glActiveTexture(GL_TEXTURE1);
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, _TEX_PAGE[shape->tcmaskpage].id);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
// TU1 RGB
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_INTERPOLATE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB, GL_TEXTURE0);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB, GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_RGB, GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_RGB, GL_SRC_ALPHA);
// TU1 Alpha
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
// This is why we are doing in opaque mode.
glEnable(GL_BLEND);
glBlendFunc(GL_CONSTANT_COLOR, GL_ZERO);
glBlendColor(colour.byte.r / 255.0, colour.byte.g / 255.0,
colour.byte.b / 255.0, colour.byte.a / 255.0);
}
#ifdef _DEBUG
glErrors();
#endif
}
for (pPolys = shape->polys; pPolys < shape->polys + shape->npolys; pPolys++)
{
@ -205,7 +284,8 @@ static void pie_Draw3DShape2(iIMDShape *shape, int frame, PIELIGHT colour, WZ_DE
polyCount++;
if (frame != 0 && pPolys->flags & iV_IMD_TEXANIM)
// Run TextureAnimation (exluding the new teamcoloured models)
if (frame && pPolys->flags & iV_IMD_TEXANIM && !(shape->flags & iV_IMD_TCMASK))
{
frame %= shape->numFrames;
@ -233,12 +313,37 @@ static void pie_Draw3DShape2(iIMDShape *shape, int frame, PIELIGHT colour, WZ_DE
for (n = 0; n < pPolys->npnts; n++)
{
glTexCoord2fv((GLfloat*)&texCoords[n]);
if (shape->flags & iV_IMD_TCMASK && rendStates.rendMode == REND_OPAQUE &&
!pie_GetShadersStatus())
{
glMultiTexCoord2fv(GL_TEXTURE1, (GLfloat*)&texCoords[n]);
}
glVertex3fv((GLfloat*)&vertexCoords[n]);
}
glEnd();
}
// Deactivate TCMask if it was previously enabled
if (shape->flags & iV_IMD_TCMASK && rendStates.rendMode == REND_OPAQUE)
{
if (pie_GetShadersStatus())
{
pie_DeactivateShader();
}
else
{
glDisable(GL_BLEND);
glActiveTexture(GL_TEXTURE1);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
glDisable(GL_TEXTURE_2D);
glActiveTexture(GL_TEXTURE0);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
}
}
if (pieFlag & pie_BUTTON)
{
pie_SetDepthBufferStatus(DEPTH_CMP_ALWAYS_WRT_ON);
@ -463,6 +568,11 @@ static void inverse_matrix(const float * src, float * dst)
dst[8] = invdet * (src[0]*src[5] - src[4]*src[1]);
}
void pie_SetUp(void)
{
// initialise pie engine (just a placeholder for now)
}
void pie_CleanUp( void )
{
free( tshapes );
@ -473,7 +583,12 @@ void pie_CleanUp( void )
void pie_Draw3DShape(iIMDShape *shape, int frame, int team, PIELIGHT colour, PIELIGHT specular, int pieFlag, int pieFlagData)
{
PIELIGHT teamcolour;
ASSERT_OR_RETURN(, shape, "Attempting to draw null sprite");
teamcolour = pal_GetTeamColour(team);
pieCount++;
if (frame == 0)
@ -483,7 +598,7 @@ void pie_Draw3DShape(iIMDShape *shape, int frame, int team, PIELIGHT colour, PIE
if (drawing_interface || !shadows)
{
pie_Draw3DShape2(shape, frame, colour, specular, pieFlag, pieFlagData);
pie_Draw3DShape2(shape, frame, colour, teamcolour, specular, pieFlag, pieFlagData);
}
else
{
@ -563,7 +678,8 @@ void pie_Draw3DShape(iIMDShape *shape, int frame, int team, PIELIGHT colour, PIE
nb_scshapes++;
}
}
pie_Draw3DShape2(shape, frame, colour, specular, pieFlag, pieFlagData);
pie_Draw3DShape2(shape, frame, colour, teamcolour, specular, pieFlag, pieFlagData);
}
}
}
@ -688,7 +804,7 @@ static void pie_DrawRemainingTransShapes(void)
for (i = 0; i < nb_tshapes; ++i)
{
glLoadMatrixf(tshapes[i].matrix);
pie_Draw3DShape2(tshapes[i].shape, tshapes[i].frame, tshapes[i].colour,
pie_Draw3DShape2(tshapes[i].shape, tshapes[i].frame, tshapes[i].colour, tshapes[i].colour,
tshapes[i].specular, tshapes[i].flag, tshapes[i].flag_data);
}
glPopMatrix();

View File

@ -58,3 +58,43 @@ void pal_ShutDown(void)
{
// placeholder
}
PIELIGHT pal_GetTeamColour(int team)
{
PIELIGHT tcolour;
// set correct team colour based on team
switch (team)
{
case 0:
tcolour = WZCOL_TEAM1; //green
break;
case 1:
tcolour = WZCOL_TEAM2; //orange
break;
case 2:
tcolour = WZCOL_TEAM3; //gray
break;
case 3:
tcolour = WZCOL_TEAM4; //black
break;
case 4:
tcolour = WZCOL_TEAM5; //red
break;
case 5:
tcolour = WZCOL_TEAM6; //blue
break;
case 6:
tcolour = WZCOL_TEAM7; //purple
break;
case 7:
tcolour = WZCOL_TEAM8; //teal
break;
default:
ASSERT(false, "Attempting to get colour for non-existing team %u", (unsigned int)team);
tcolour = WZCOL_WHITE; //default is white
break;
}
return tcolour;
}

View File

@ -26,12 +26,14 @@
#include <SDL.h>
#include <SDL_mouse.h>
#include <physfs.h>
#include "lib/ivis_common/piestate.h"
#include "lib/ivis_common/piedef.h"
#include "lib/ivis_common/tex.h"
#include "lib/ivis_common/piepalette.h"
#include "lib/ivis_common/rendmode.h"
#include "screen.h"
/*
* Global Variables
@ -43,11 +45,229 @@ static bool ColouredMouse = false;
static IMAGEFILE* MouseCursors = NULL;
static uint16_t MouseCursorIDs[CURSOR_MAX];
static bool MouseVisible = true;
static GLuint shaderProgram[SHADER_MAX];
static bool shadersAvailable = false; // Can we use shaders?
static bool shadersActivate = true; // If we can, should we use them?
/*
* Source
*/
// Read shader into text buffer
static char *readShaderBuf(const char *name)
{
PHYSFS_file *fp;
int filesize;
char *buffer;
fp = PHYSFS_openRead(name);
debug(LOG_3D, "Reading...[directory: %s] %s", PHYSFS_getRealDir(name), name);
ASSERT_OR_RETURN(0, fp != NULL, "Could not open %s", name);
filesize = PHYSFS_fileLength(fp);
buffer = malloc(filesize + 1);
if (buffer)
{
PHYSFS_read(fp, buffer, 1, filesize);
buffer[filesize] = '\0';
}
PHYSFS_close(fp);
return buffer;
}
// Retrieve shader compilation errors
static void printShaderInfoLog(GLuint shader)
{
GLint infologLen = 0;
glGetShaderiv(shader, GL_INFO_LOG_LENGTH, &infologLen);
if (infologLen > 0)
{
GLint charsWritten = 0;
GLchar *infoLog = (GLchar *)malloc(infologLen);
glGetShaderInfoLog(shader, infologLen, &charsWritten, infoLog);
debug(LOG_ERROR, "Shader info log: %s", infoLog);
free(infoLog);
}
}
// Retrieve shader linkage errors
static void printProgramInfoLog(GLuint program)
{
GLint infologLen = 0;
glGetProgramiv(program, GL_INFO_LOG_LENGTH, &infologLen);
if (infologLen > 0)
{
GLint charsWritten = 0;
GLchar *infoLog = (GLchar *)malloc(infologLen);
glGetProgramInfoLog(program, infologLen, &charsWritten, infoLog);
debug(LOG_ERROR, "Program info log: %s", infoLog);
free(infoLog);
}
}
// Read/compile/link shaders
static bool loadShaders(GLuint *program, const char *vertexPath, const char *fragmentPath)
{
GLint status;
bool success = true; // Assume overall success
char *buffer;
*program = glCreateProgram();
ASSERT_OR_RETURN(false, *program != 0, "Could not create shader program");
if (vertexPath)
{
success = false; // Assume failure before reading shader file
if ((buffer = readShaderBuf(vertexPath)))
{
GLuint shader = glCreateShader(GL_VERTEX_SHADER);
glShaderSource(shader, 1, (const char **)&buffer, NULL);
glCompileShader(shader);
// Check for compilation errors
glGetShaderiv(shader, GL_COMPILE_STATUS, &status);
if (!status)
{
debug(LOG_ERROR, "Vertex shader compilation has failed [%s]", vertexPath);
printShaderInfoLog(shader);
}
else
{
glAttachShader(*program, shader);
success = true;
}
free(buffer);
}
}
if (success && fragmentPath)
{
success = false; // Assume failure before reading shader file
if ((buffer = readShaderBuf(fragmentPath)))
{
GLuint shader = glCreateShader(GL_FRAGMENT_SHADER);
glShaderSource(shader, 1, (const char **)&buffer, NULL);
glCompileShader(shader);
// Check for compilation errors
glGetShaderiv(shader, GL_COMPILE_STATUS, &status);
if (!status)
{
debug(LOG_ERROR, "Fragment shader compilation has failed [%s]", fragmentPath);
printShaderInfoLog(shader);
}
else
{
glAttachShader(*program, shader);
success = true;
}
free(buffer);
}
}
if (success)
{
glLinkProgram(*program);
// Check for linkage errors
glGetProgramiv(*program, GL_LINK_STATUS, &status);
if (!status)
{
debug(LOG_ERROR, "Shader program linkage has failed [%s, %s]", vertexPath, fragmentPath);
printProgramInfoLog(*program);
success = false;
}
}
return success;
}
// Run from screen.c on init. FIXME: do some kind of FreeShaders on failure.
bool pie_LoadShaders()
{
GLuint program;
// Reset shaders status
shadersAvailable = false;
// Try and load some shaders
shaderProgram[SHADER_NONE] = 0;
// TCMask shader
debug(LOG_3D, "Loading shaders: SHADER_TCMASK");
if (!loadShaders(&program, "shaders/tcmask.vert", "shaders/tcmask.frag"))
return false;
shaderProgram[SHADER_TCMASK] = program;
// Good to go
shadersAvailable = true;
return true;
}
static inline GLuint pie_SetShader(SHADER_MODE shaderMode)
{
if (!shadersAvailable || shaderMode >= SHADER_MAX)
return shaderProgram[SHADER_NONE];
glUseProgram(shaderProgram[shaderMode]);
return shaderProgram[shaderMode];
}
void pie_DeactivateShader(void)
{
pie_SetShader(SHADER_NONE);
}
bool pie_GetShadersStatus(void)
{
return shadersAvailable && shadersActivate;
}
void pie_SetShadersStatus(bool status)
{
shadersActivate = status;
}
void pie_ActivateShader_TCMask(PIELIGHT teamcolour, SDWORD maskpage)
{
GLint loc;
GLuint shaderProgram;
GLfloat colour4f[4];
if (!shadersAvailable)
return;
shaderProgram = pie_SetShader(SHADER_TCMASK);
loc = glGetUniformLocation(shaderProgram, "Texture0");
glUniform1i(loc, 0);
loc = glGetUniformLocation(shaderProgram, "Texture1");
glUniform1i(loc, 1);
loc = glGetUniformLocation(shaderProgram, "teamcolour");
pal_PIELIGHTtoRGBA4f(&colour4f[0], teamcolour);
glUniform4fv(loc, 1, &colour4f[0]);
glActiveTexture(GL_TEXTURE1);
pie_SetTexturePage(maskpage);
glActiveTexture(GL_TEXTURE0);
#ifdef _DEBUG
glErrors();
#endif
}
void pie_SetDepthBufferStatus(DEPTH_MODE depthMode)
{
switch(depthMode)

View File

@ -78,6 +78,8 @@ bool screenInitialise(
{
static int video_flags = 0;
int bpp = 0, value;
char buf[512];
GLint glMaxTUs;
/* Store the screen information */
screenWidth = width;
@ -162,51 +164,49 @@ bool screenInitialise(
exit(1);
}
{
char buf[256];
/* Dump general information about OpenGL implementation to the console and the dump file */
ssprintf(buf, "OpenGL Vendor : %s", glGetString(GL_VENDOR));
addDumpInfo(buf);
debug(LOG_3D, buf);
ssprintf(buf, "OpenGL Renderer : %s", glGetString(GL_RENDERER));
addDumpInfo(buf);
debug(LOG_3D, buf);
ssprintf(buf, "OpenGL Version : %s", glGetString(GL_VERSION));
addDumpInfo(buf);
debug(LOG_3D, buf);
ssprintf(buf, "Video Mode %d x %d (%d bpp) (%s)", width, height, bpp, fullScreen ? "fullscreen" : "window");
addDumpInfo(buf);
debug(LOG_3D, buf);
// Copy this info to be used by the crash handler for the dump file
ssprintf(buf, "OpenGL Vendor : %s", glGetString(GL_VENDOR));
addDumpInfo(buf);
ssprintf(buf, "OpenGL Renderer : %s", glGetString(GL_RENDERER));
addDumpInfo(buf);
ssprintf(buf, "OpenGL Version : %s", glGetString(GL_VERSION));
addDumpInfo(buf);
if (GLEE_VERSION_2_0)
{
ssprintf(buf, "OpenGL GLSL Version : %s", glGetString(GL_SHADING_LANGUAGE_VERSION));
addDumpInfo(buf);
}
ssprintf(buf, "Video Mode %d x %d (%d bpp) (%s)", width, height, bpp, fullScreen ? "fullscreen" : "window");
addDumpInfo(buf);
/* Dump information about OpenGL implementation to the console */
debug(LOG_3D, "OpenGL Vendor : %s", glGetString(GL_VENDOR));
debug(LOG_3D, "OpenGL Renderer : %s", glGetString(GL_RENDERER));
debug(LOG_3D, "OpenGL Version : %s", glGetString(GL_VERSION));
debug(LOG_3D, "OpenGL Extensions : %s", glGetString(GL_EXTENSIONS)); // FIXME This is too much for MAX_LEN_LOG_LINE
debug(LOG_3D, "Supported OpenGL extensions:");
debug(LOG_3D, " * OpenGL 1.2 %s supported!", GLEE_VERSION_1_2 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 1.3 %s supported!", GLEE_VERSION_1_3 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 1.4 %s supported!", GLEE_VERSION_1_4 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 1.5 %s supported!", GLEE_VERSION_1_5 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 2.0 %s supported!", GLEE_VERSION_2_0 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 2.1 %s supported!", GLEE_VERSION_2_1 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 3.0 %s supported!", GLEE_VERSION_3_0 ? "is" : "is NOT");
debug(LOG_3D, " * Texture compression %s supported.", GLEE_ARB_texture_compression ? "is" : "is NOT");
debug(LOG_3D, " * Two side stencil %s supported.", GLEE_EXT_stencil_two_side ? "is" : "is NOT");
debug(LOG_3D, " * ATI separate stencil is%s supported.", GLEE_ATI_separate_stencil ? "" : " NOT");
debug(LOG_3D, " * Stencil wrap %s supported.", GLEE_EXT_stencil_wrap ? "is" : "is NOT");
debug(LOG_3D, " * Anisotropic filtering %s supported.", GLEE_EXT_texture_filter_anisotropic ? "is" : "is NOT");
debug(LOG_3D, " * Rectangular texture %s supported.", GLEE_ARB_texture_rectangle ? "is" : "is NOT");
debug(LOG_3D, " * FrameBuffer Object (FBO) %s supported.", GLEE_EXT_framebuffer_object ? "is" : "is NOT");
debug(LOG_3D, " * Shader Objects %s supported.", GL_ARB_shader_objects ? "is" : "is NOT");
debug(LOG_3D, " * Vertex Buffer Object (VBO) %s supported.", GL_ARB_vertex_buffer_object ? "is" : "is NOT");
if (GLEE_VERSION_2_0)
{
debug(LOG_3D, " * OpenGL GLSL Version : %s", glGetString(GL_SHADING_LANGUAGE_VERSION));
}
}
/* Dump extended information about OpenGL implementation to the console */
debug(LOG_3D, "OpenGL Extensions : %s", glGetString(GL_EXTENSIONS)); // FIXME This is too much for MAX_LEN_LOG_LINE
debug(LOG_3D, "Supported OpenGL extensions:");
debug(LOG_3D, " * OpenGL 1.2 %s supported!", GLEE_VERSION_1_2 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 1.3 %s supported!", GLEE_VERSION_1_3 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 1.4 %s supported!", GLEE_VERSION_1_4 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 1.5 %s supported!", GLEE_VERSION_1_5 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 2.0 %s supported!", GLEE_VERSION_2_0 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 2.1 %s supported!", GLEE_VERSION_2_1 ? "is" : "is NOT");
debug(LOG_3D, " * OpenGL 3.0 %s supported!", GLEE_VERSION_3_0 ? "is" : "is NOT");
debug(LOG_3D, " * Texture compression %s supported.", GLEE_ARB_texture_compression ? "is" : "is NOT");
debug(LOG_3D, " * Two side stencil %s supported.", GLEE_EXT_stencil_two_side ? "is" : "is NOT");
debug(LOG_3D, " * ATI separate stencil is%s supported.", GLEE_ATI_separate_stencil ? "" : " NOT");
debug(LOG_3D, " * Stencil wrap %s supported.", GLEE_EXT_stencil_wrap ? "is" : "is NOT");
debug(LOG_3D, " * Anisotropic filtering %s supported.", GLEE_EXT_texture_filter_anisotropic ? "is" : "is NOT");
debug(LOG_3D, " * Rectangular texture %s supported.", GLEE_ARB_texture_rectangle ? "is" : "is NOT");
debug(LOG_3D, " * FrameBuffer Object (FBO) %s supported.", GLEE_EXT_framebuffer_object ? "is" : "is NOT");
debug(LOG_3D, " * Shader Objects %s supported.", GL_ARB_shader_objects ? "is" : "is NOT");
debug(LOG_3D, " * Vertex Buffer Object (VBO) %s supported.", GL_ARB_vertex_buffer_object ? "is" : "is NOT");
glGetIntegerv(GL_MAX_TEXTURE_UNITS, &glMaxTUs);
debug(LOG_3D, " * Total number of Texture Units (TUs) supported is %d.", (int) glMaxTUs);
if (!GLEE_VERSION_1_4)
{
debug(LOG_FATAL, "OpenGL 1.4+ is required for this game!");
exit(1);
}
#ifndef WZ_OS_MAC
// Make OpenGL's VBO functions available under the core names for
// implementations that have them only as extensions, namely Mesa.
@ -230,6 +230,26 @@ bool screenInitialise(
}
#endif
/* Dump information about OpenGL 2.0+ implementation to the console and the dump file */
if (GLEE_VERSION_2_0)
{
GLint glMaxTIUs;
debug(LOG_3D, " * OpenGL GLSL Version : %s", glGetString(GL_SHADING_LANGUAGE_VERSION));
ssprintf(buf, "OpenGL GLSL Version : %s", glGetString(GL_SHADING_LANGUAGE_VERSION));
addDumpInfo(buf);
glGetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS, &glMaxTIUs);
debug(LOG_3D, " * Total number of Texture Image Units (TIUs) supported is %d.", (int) glMaxTIUs);
if (!pie_LoadShaders())
debug(LOG_WARNING, "Can't use shaders! Switching back to fixed pipeline...");;
}
else
{
debug(LOG_WARNING, "OpenGL 2.0 is not supported by your system! Using fixed pipeline...");
}
glViewport(0, 0, width, height);
glMatrixMode(GL_PROJECTION);
glPushMatrix();

View File

@ -57,12 +57,13 @@ static void pie_PrintLoadedTextures(void);
Returns the texture number of the image.
**************************************************************************/
int pie_AddTexPage(iV_Image *s, const char* filename, int slot, int maxTextureSize)
int pie_AddTexPage(iV_Image *s, const char* filename, int slot, int maxTextureSize, bool useMipmaping)
{
unsigned int i = 0;
int width, height;
void *bmp;
bool scaleDown = false;
GLint minfilter;
/* Have we already loaded this one? Should not happen here. */
while (i < _TEX_INDEX)
@ -130,14 +131,28 @@ int pie_AddTexPage(iV_Image *s, const char* filename, int slot, int maxTextureSi
// this is an interface texture, do not use compression
gluBuild2DMipmaps(GL_TEXTURE_2D, GL_RGBA, width, height, iV_getPixelFormat(s), GL_UNSIGNED_BYTE, bmp);
}
} else {
}
else
{
debug(LOG_ERROR, "pie_AddTexPage: non POT texture %s", filename);
}
free(bmp); // it is uploaded, we do not need it anymore
// it is uploaded, we do not need it anymore
free(bmp);
s->bmp = NULL;
if (useMipmaping)
{
minfilter = GL_LINEAR_MIPMAP_LINEAR;
}
else
{
minfilter = GL_LINEAR;
}
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, minfilter);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
// Use anisotropic filtering, if available, but only max 4.0 to reduce processor burden
@ -181,6 +196,20 @@ void pie_MakeTexPageName(char * filename)
}
}
/*!
* Turns page filename into a pagename + tc mask if possible
* \param[in,out] filename Filename to pagify
*/
void pie_MakeTexPageTCMaskName(char * filename)
{
if (strncmp(filename, "page-", 5) == 0)
{
int i;
for( i = 5; i < iV_TEXNAME_MAX-1 && isdigit(filename[i]); i++);
filename[i] = '\0';
strcat(filename, iV_TEXNAME_TCSUFFIX);
}
}
/*!
* Print the names of all loaded textures to LOG_ERROR
@ -236,7 +265,7 @@ int iV_GetTexture(const char *filename)
replaceing the texture page with the same name if another file
with this prefix is loaded.
**************************************************************************/
int pie_ReplaceTexPage(iV_Image *s, const char *texPage, int maxTextureSize)
int pie_ReplaceTexPage(iV_Image *s, const char *texPage, int maxTextureSize, bool useMipmaping)
{
int i = iV_GetTexture(texPage);
@ -249,7 +278,7 @@ int pie_ReplaceTexPage(iV_Image *s, const char *texPage, int maxTextureSize)
glDeleteTextures(1, &_TEX_PAGE[i].id);
debug(LOG_TEXTURE, "Reloading texture %s from index %d", texPage, i);
_TEX_PAGE[i].name[0] = '\0';
pie_AddTexPage(s, texPage, i, maxTextureSize);
pie_AddTexPage(s, texPage, i, maxTextureSize, useMipmaping);
return i;
}

View File

@ -140,7 +140,7 @@
022B2FA80BD55B50002E64E3 /* vasnwprintf.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B2F950BD55B50002E64E3 /* vasnwprintf.h */; };
022B2FA90BD55B50002E64E3 /* wprintf-parse.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B2F960BD55B50002E64E3 /* wprintf-parse.h */; };
022B2FAA0BD55B50002E64E3 /* xsize.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B2F970BD55B50002E64E3 /* xsize.h */; };
022B2FE20BD55E45002E64E3 /* libgnuintl.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B2FE00BD55E45002E64E3 /* libgnuintl.h */; };
022B2FE20BD55E45002E64E3 /* libgnuintl.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B2FE00BD55E45002E64E3 /* libgnuintl.h */; settings = {ATTRIBUTES = (Public, ); }; };
022B2FE30BD55E45002E64E3 /* libintl.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B2FE10BD55E45002E64E3 /* libintl.h */; settings = {ATTRIBUTES = (Public, ); }; };
022B30AB0BD564FC002E64E3 /* config.h in Headers */ = {isa = PBXBuildFile; fileRef = 022B30AA0BD564FC002E64E3 /* config.h */; };
022B30E00BD56618002E64E3 /* plural.c in Sources */ = {isa = PBXBuildFile; fileRef = 022B30DF0BD56618002E64E3 /* plural.c */; };
@ -170,7 +170,7 @@
02356DB50BD3BB6F00E9A019 /* zutil.h in Headers */ = {isa = PBXBuildFile; fileRef = 02356D9F0BD3BB6F00E9A019 /* zutil.h */; settings = {ATTRIBUTES = (); }; };
02356DDB0BD3BC9900E9A019 /* png.c in Sources */ = {isa = PBXBuildFile; fileRef = 02356DC90BD3BC9900E9A019 /* png.c */; };
02356DDC0BD3BC9900E9A019 /* png.h in Headers */ = {isa = PBXBuildFile; fileRef = 02356DCA0BD3BC9900E9A019 /* png.h */; settings = {ATTRIBUTES = (Public, ); }; };
02356DDD0BD3BC9900E9A019 /* pngconf.h in Headers */ = {isa = PBXBuildFile; fileRef = 02356DCB0BD3BC9900E9A019 /* pngconf.h */; settings = {ATTRIBUTES = (); }; };
02356DDD0BD3BC9900E9A019 /* pngconf.h in Headers */ = {isa = PBXBuildFile; fileRef = 02356DCB0BD3BC9900E9A019 /* pngconf.h */; settings = {ATTRIBUTES = (Public, ); }; };
02356DDE0BD3BC9900E9A019 /* pngerror.c in Sources */ = {isa = PBXBuildFile; fileRef = 02356DCC0BD3BC9900E9A019 /* pngerror.c */; };
02356DE00BD3BC9900E9A019 /* pngget.c in Sources */ = {isa = PBXBuildFile; fileRef = 02356DCE0BD3BC9900E9A019 /* pngget.c */; };
02356DE10BD3BC9900E9A019 /* pngmem.c in Sources */ = {isa = PBXBuildFile; fileRef = 02356DCF0BD3BC9900E9A019 /* pngmem.c */; };

View File

@ -3,7 +3,7 @@
INSTALL_PATH = $(HOME)/Applications
COPY_PHASE_STRIP = NO
OTHER_LDFLAGS[arch=ppc] = -w
OTHER_LDFLAGS[arch=ppc] = -w // This turns off 2 warnings that are actually in apple's sdk.
PREBINDING = NO
INFOPLIST_FILE = Resources/Warzone-Info.plist
INFOPLIST_OTHER_PREPROCESSOR_FLAGS = -traditional

View File

@ -9,7 +9,7 @@
force-linker.cpp:
touch $@
AM_CPPFLAGS = -DYY_NO_INPUT $(SDL_CFLAGS) $(PHYSFS_CFLAGS) $(PNG_CFLAGS) $(OGGVORBIS_CFLAGS) $(OPENAL_CFLAGS) $(OPENGLC_CFLAGS) $(OPENGL_CFLAGS) $(POPT_CFLAGS) $(WZ_CPPFLAGS) $(GLee_CFLAGS)
AM_CPPFLAGS = -DYY_NO_INPUT $(SDL_CFLAGS) $(PHYSFS_CFLAGS) $(PNG_CFLAGS) $(OGGVORBIS_CFLAGS) $(OPENAL_CFLAGS) $(OPENGLC_CFLAGS) $(OPENGL_CFLAGS) $(WZ_CPPFLAGS) $(GLee_CFLAGS)
AM_CFLAGS = $(WZ_CFLAGS)
AM_CXXFLAGS = $(WZ_CXXFLAGS)
AM_LFLAGS = $(FLEX_FLAGS)
@ -303,7 +303,7 @@ warzone2100_LDADD = \
$(top_builddir)/lib/iniparser/libiniparser.a \
$(top_builddir)/lib/exceptionhandler/libexceptionhandler.a
warzone2100_LDADD += $(LTLIBINTL) $(SDL_LIBS) $(PHYSFS_LIBS) $(PNG_LIBS) $(OGGVORBIS_LIBS) $(THEORA_LIBS) $(OPENAL_LIBS) $(OPENGLC_LIBS) $(OPENGL_LIBS) $(POPT_LIBS) $(X11_LIBS) $(GLee_LIBS)
warzone2100_LDADD += $(LTLIBINTL) $(SDL_LIBS) $(PHYSFS_LIBS) $(PNG_LIBS) $(OGGVORBIS_LIBS) $(THEORA_LIBS) $(OPENAL_LIBS) $(OPENGLC_LIBS) $(OPENGL_LIBS) $(X11_LIBS) $(GLee_LIBS)
if MINGW32
warzone2100_LDADD += $(top_builddir)/win32/warzone2100.o $(WIN32_LIBS)

View File

@ -24,8 +24,6 @@
*
*/
#include <popt.h>
#include "lib/framework/frame.h"
#include "lib/netplay/netplay.h"
@ -43,6 +41,160 @@
//! Let the end user into debug mode....
BOOL bAllowDebugMode = false;
//////
// Our fine replacement for the popt abomination follows
#define POPT_ARG_STRING true
#define POPT_ARG_NONE false
#define POPT_ERROR_BADOPT -1
struct poptOption
{
const char *string;
char short_form;
bool argument;
void *nullptr; // unused
int enumeration;
const char *descrip;
const char *argDescrip;
};
typedef struct _poptContext
{
int argc, current, size;
const char **argv;
const char *parameter;
const char *bad;
const struct poptOption *table;
} *poptContext;
static void poptPrintHelp(poptContext ctx, FILE *output, WZ_DECL_UNUSED int unused)
{
int i;
fprintf(output, "Usage: %s [OPTION...]\n", ctx->argv[0]);
for (i = 0; i < ctx->size; i++)
{
char txt[128];
if (ctx->table[i].short_form != '\0')
{
ssprintf(txt, " -%c, --%s", ctx->table[i].short_form, ctx->table[i].string);
}
else
{
ssprintf(txt, " --%s", ctx->table[i].string);
}
if (ctx->table[i].argument)
{
sstrcat(txt, "=");
sstrcat(txt, ctx->table[i].argDescrip);
}
fprintf(output, "%-40s", txt);
if (ctx->table[i].descrip)
{
fprintf(output, "%s", ctx->table[i].descrip);
}
fprintf(output, "\n");
}
}
static const char *poptBadOption(poptContext ctx, WZ_DECL_UNUSED int unused)
{
return ctx->bad;
}
static const char *poptGetOptArg(poptContext ctx)
{
return ctx->parameter;
}
static int poptGetNextOpt(poptContext ctx)
{
static char match[PATH_MAX]; // static for bad function
static char parameter[PATH_MAX]; // static for arg function
char *pparam;
int i;
ctx->bad = NULL;
ctx->parameter = NULL;
parameter[0] = '\0';
match[0] = '\0';
if (ctx->current >= ctx->argc) // counts from 1
{
return 0;
}
sstrcpy(match, ctx->argv[ctx->current]);
ctx->current++;
pparam = strrchr(match, '=');
if (pparam) // option's got a parameter
{
*pparam++ = '\0'; // split option from parameter and increment past '='
if (pparam[0] == '"') // found scary quotes
{
pparam++; // skip start quote
sstrcpy(parameter, pparam); // copy first parameter
if (!strrchr(pparam, '"')) // if no end quote, then find it
{
while (!strrchr(parameter, '"') && ctx->current < ctx->argc)
{
sstrcat(parameter, " "); // insert space
sstrcat(parameter, ctx->argv[ctx->current]);
ctx->current++; // next part, please!
}
}
if (strrchr(parameter, '"')) // its not an else for above!
{
*strrchr(parameter, '"') = '\0'; // remove end qoute
}
}
else
{
sstrcpy(parameter, pparam); // copy parameter
}
}
for (i = 0; i < ctx->size; i++)
{
char sshort[3];
char slong[64];
ssprintf(sshort, "-%c", ctx->table[i].short_form);
ssprintf(slong, "--%s", ctx->table[i].string);
if ((strcmp(sshort, match) == 0 && ctx->table[i].short_form != '\0') || strcmp(slong, match) == 0)
{
if (ctx->table[i].argument && pparam)
{
ctx->parameter = parameter;
}
return ctx->table[i].enumeration;
}
}
ctx->bad = match;
ctx->current++;
return POPT_ERROR_BADOPT;
}
static poptContext poptGetContext(WZ_DECL_UNUSED void *unused, int argc, const char **argv, const struct poptOption *table, WZ_DECL_UNUSED int none)
{
static struct _poptContext ctx;
ctx.argc = argc;
ctx.argv = argv;
ctx.table = table;
ctx.current = 1;
ctx.parameter = NULL;
for (ctx.size = 0; table[ctx.size].string; ctx.size++) ; // count table size
return &ctx;
}
typedef enum
{
// We don't want to use zero, so start at one (1)
@ -59,7 +211,6 @@ typedef enum
CLI_MOD_CA,
CLI_MOD_MP,
CLI_SAVEGAME,
CLI_USAGE,
CLI_WINDOW,
CLI_VERSION,
CLI_RESOLUTION,
@ -79,8 +230,8 @@ static const struct poptOption* getOptionsTable(void)
static const struct poptOption optionsTable[] =
{
{ "cheat", '\0', POPT_ARG_NONE, NULL, CLI_CHEAT, N_("Run in cheat mode"), NULL },
{ "datadir", '\0', POPT_ARG_STRING, NULL, CLI_DATADIR, N_("Set default data directory"), N_("data directory") },
{ "configdir", '\0', POPT_ARG_STRING, NULL, CLI_CONFIGDIR, N_("Set configuration directory"), N_("configuration directory") },
{ "datadir", '\0', POPT_ARG_STRING, NULL, CLI_DATADIR, N_("Set default data directory"), N_("data directory") },
{ "debug", '\0', POPT_ARG_STRING, NULL, CLI_DEBUG, N_("Show debug for given level"), N_("debug level") },
{ "debugfile", '\0', POPT_ARG_STRING, NULL, CLI_DEBUGFILE, N_("Log debug output to file"), N_("file") },
{ "flush-debug-stderr", '\0', POPT_ARG_NONE, NULL, CLI_FLUSHDEBUGSTDERR, N_("Flush all debug output written to stderr"), NULL },
@ -93,8 +244,6 @@ static const struct poptOption* getOptionsTable(void)
{ "noassert", '\0', POPT_ARG_NONE, NULL, CLI_NOASSERT, N_("Disable asserts"), NULL },
{ "crash", '\0', POPT_ARG_NONE, NULL, CLI_CRASH, N_("Causes a crash to test the crash handler"), NULL },
{ "savegame", '\0', POPT_ARG_STRING, NULL, CLI_SAVEGAME, N_("Load a saved game"), N_("savegame") },
{ "usage", '\0', POPT_ARG_NONE
| POPT_ARGFLAG_DOC_HIDDEN, NULL, CLI_USAGE, NULL, NULL, },
{ "window", '\0', POPT_ARG_NONE, NULL, CLI_WINDOW, N_("Play in windowed mode"), NULL },
{ "version", '\0', POPT_ARG_NONE, NULL, CLI_VERSION, N_("Show version information and exit"), NULL },
{ "resolution", '\0', POPT_ARG_STRING, NULL, CLI_RESOLUTION, N_("Set the resolution to use"), N_("WIDTHxHEIGHT") },
@ -173,7 +322,6 @@ bool ParseCommandLineEarly(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Usage: --debug <flag>");
poptFreeContext(poptCon);
return false;
}
@ -181,7 +329,6 @@ bool ParseCommandLineEarly(int argc, const char** argv)
if (!debug_enable_switch(token))
{
debug(LOG_ERROR, "Debug flag \"%s\" not found!", token);
poptFreeContext(poptCon);
return false;
}
break;
@ -192,7 +339,6 @@ bool ParseCommandLineEarly(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Missing debugfile filename?");
poptFreeContext(poptCon);
return false;
}
debug_register_callback( debug_callback_file, debug_callback_file_init, debug_callback_file_exit, (void*)token );
@ -209,7 +355,6 @@ bool ParseCommandLineEarly(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Unrecognised configuration directory");
poptFreeContext(poptCon);
return false;
}
sstrcpy(configdir, token);
@ -217,17 +362,10 @@ bool ParseCommandLineEarly(int argc, const char** argv)
case CLI_HELP:
poptPrintHelp(poptCon, stdout, 0);
poptFreeContext(poptCon);
return false;
case CLI_USAGE:
poptPrintUsage(poptCon, stdout, 0);
poptFreeContext(poptCon);
return false;
case CLI_VERSION:
printf("Warzone 2100 - %s\n", version_getFormattedVersionString());
poptFreeContext(poptCon);
return false;
default:
@ -235,8 +373,6 @@ bool ParseCommandLineEarly(int argc, const char** argv)
};
}
poptFreeContext(poptCon);
return true;
}
@ -265,7 +401,6 @@ bool ParseCommandLine(int argc, const char** argv)
case CLI_FLUSHDEBUGSTDERR:
case CLI_CONFIGDIR:
case CLI_HELP:
case CLI_USAGE:
case CLI_VERSION:
// These options are parsed in ParseCommandLineEarly() already, so ignore them
break;
@ -293,7 +428,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Unrecognised datadir");
poptFreeContext(poptCon);
return false;
}
sstrcpy(datadir, token);
@ -308,7 +442,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "No IP/hostname given");
poptFreeContext(poptCon);
return false;
}
sstrcpy(iptoconnect, token);
@ -323,7 +456,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "No game name");
poptFreeContext(poptCon);
return false;
}
if (strcmp(token, "CAM_1A") && strcmp(token, "CAM_2A") && strcmp(token, "CAM_3A")
@ -358,7 +490,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Missing mod name?");
poptFreeContext(poptCon);
return false;
}
@ -367,7 +498,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (i >= 100 || global_mods[i] != NULL)
{
debug(LOG_ERROR, "Too many mods registered! Aborting!");
poptFreeContext(poptCon);
return false;
}
global_mods[i] = strdup(token);
@ -382,7 +512,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Missing mod name?");
poptFreeContext(poptCon);
return false;
}
@ -391,7 +520,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (i >= 100 || campaign_mods[i] != NULL)
{
debug(LOG_ERROR, "Too many mods registered! Aborting!");
poptFreeContext(poptCon);
return false;
}
campaign_mods[i] = strdup(token);
@ -406,7 +534,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Missing mod name?");
poptFreeContext(poptCon);
return false;
}
@ -414,7 +541,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (i >= 100 || multiplay_mods[i] != NULL)
{
debug(LOG_ERROR, "Too many mods registered! Aborting!");
poptFreeContext(poptCon);
return false;
}
multiplay_mods[i] = strdup(token);
@ -452,7 +578,6 @@ bool ParseCommandLine(int argc, const char** argv)
if (token == NULL)
{
debug(LOG_ERROR, "Unrecognised savegame name");
poptFreeContext(poptCon);
return false;
}
snprintf(saveGameName, sizeof(saveGameName), "%s/%s", SaveGamePath, token);
@ -485,7 +610,5 @@ bool ParseCommandLine(int argc, const char** argv)
};
}
poptFreeContext(poptCon);
return true;
}

View File

@ -43,6 +43,9 @@
#include "text.h"
#include "texture.h"
#define DT_TEXPAGE "TEXPAGE"
#define DT_TCMASK "TCMASK"
// whether a save game is currently being loaded
static bool saveFlag = false;
@ -779,17 +782,53 @@ static bool dataTexPageLoad(const char *fileName, void **ppData)
}
// see if this texture page has already been loaded
if (resPresent("TEXPAGE", texpage))
if (resPresent(DT_TEXPAGE, texpage))
{
// replace the old texture page with the new one
debug(LOG_TEXTURE, "replacing %s with new texture %s", texpage, fileName);
(void) pie_ReplaceTexPage(*ppData, texpage, getTextureSize());
(void) pie_ReplaceTexPage(*ppData, texpage, getTextureSize(), true);
}
else
{
debug(LOG_TEXTURE, "adding page %s with texture %s", texpage, fileName);
SetLastResourceFilename(texpage);
(void) pie_AddTexPage(*ppData, texpage, 0, getTextureSize());
(void) pie_AddTexPage(*ppData, texpage, 0, getTextureSize(), true);
}
return true;
}
/* Load a team colour mask texturepage into memory */
static bool dataTexPageTCMaskLoad(const char *fileName, void **ppData)
{
char texpage[PATH_MAX] = {'\0'};
// This hackery is needed, because fileName will include the directory name, whilst the LastResourceFilename will not, and we need a short name to identify the texpage
sstrcpy(texpage, GetLastResourceFilename());
// Check if a corresponding texpage exists, exit if no
pie_MakeTexPageName(texpage);
ASSERT_OR_RETURN(false, resPresent(DT_TEXPAGE, texpage), "Corresponding texpage %s doesn't exists!", texpage);
pie_MakeTexPageTCMaskName(texpage);
if (!dataImageLoad(fileName, ppData))
{
return false;
}
// see if this texture page has already been loaded
if (resPresent(DT_TCMASK, texpage))
{
// replace the old texture page with the new one
debug(LOG_TEXTURE, "replacing %s with new tcmask %s", texpage, fileName);
(void) pie_ReplaceTexPage(*ppData, texpage, getTextureSize(), false);
}
else
{
debug(LOG_TEXTURE, "adding page %s with tcmask %s", texpage, fileName);
SetLastResourceFilename(texpage);
(void) pie_AddTexPage(*ppData, texpage, 0, getTextureSize(), false);
}
return true;
@ -1106,11 +1145,12 @@ static const RES_TYPE_MIN_FILE FileResourceTypes[] =
{"IMGPAGE", dataImageLoad, dataImageRelease},
{"TERTILES", dataTERTILESLoad, dataTERTILESRelease},
{"IMG", dataIMGLoad, dataIMGRelease},
{"TEXPAGE", dataTexPageLoad, dataImageRelease},
{DT_TEXPAGE, dataTexPageLoad, dataImageRelease},
{DT_TCMASK, dataTexPageTCMaskLoad, dataImageRelease},
{"SCRIPT", dataScriptLoad, dataScriptRelease},
{"SCRIPTVAL", dataScriptLoadVals, NULL},
{"STR_RES", dataStrResLoad, dataStrResRelease},
{ "RESEARCHMSG", dataResearchMsgLoad, dataSMSGRelease },
{"RESEARCHMSG", dataResearchMsgLoad, dataSMSGRelease },
};
/* Pass all the data loading functions to the framework library */

View File

@ -740,6 +740,7 @@ static void drawTiles(iView *player)
{
UDWORD i, j;
SDWORD rx, rz;
Vector3f theSun;
/* ---------------------------------------------------------------- */
/* Do boundary and extent checking */
@ -778,12 +779,9 @@ static void drawTiles(iView *player)
/* Translate */
pie_TRANSLATE(-rx, -player->p.y, rz);
if (getDrawShadows())
{
Vector3f theSun = getTheSun();
// this also detemines the length of the shadows
pie_BeginLighting(&theSun);
}
// this also detemines the length of the shadows
theSun = getTheSun();
pie_BeginLighting(&theSun, getDrawShadows());
// update the fog of war
for (i = 0; i < visibleTiles.y+1; i++)
@ -842,7 +840,12 @@ static void drawTiles(iView *player)
drawTerrain();
// go back to the warzone [0,255] range
glActiveTexture(GL_TEXTURE1);
pie_TranslateTextureEnd();
// go back to the warzone [0,255] range
glActiveTexture(GL_TEXTURE0);
pie_TranslateTextureEnd();
// and to the warzone modelview transform
glPopMatrix();
@ -895,7 +898,12 @@ static void drawTiles(iView *player)
drawWater();
// go back to the warzone [0,255] range
glActiveTexture(GL_TEXTURE1);
pie_TranslateTextureEnd();
// go back to the warzone [0,255] range
glActiveTexture(GL_TEXTURE0);
pie_TranslateTextureEnd();
// and to the warzone modelview transform
glPopMatrix();

108
src/hci.c
View File

@ -35,6 +35,7 @@
#include "lib/gamelib/gtime.h"
#include "lib/ivis_common/rendmode.h"
#include "lib/ivis_common/piepalette.h"
#include "lib/ivis_common/piestate.h"
// FIXME Direct iVis implementation include!
#include "lib/ivis_opengl/screen.h"
#include "lib/script/script.h"
@ -177,9 +178,13 @@ BOOL Refreshing = false;
#define IDOPT_DROID 1037 // The place droid button
#define IDOPT_STRUCT 1038 // The place struct button
#define IDOPT_FEATURE 1039 // The place feature button
#define IDOPT_TILE 1040 // The place tile button
#define IDOPT_PAUSE 1041 // The edit pause button
#define IDOPT_TILE 1040 // The place tile button
#define IDOPT_PAUSE 1041 // The edit pause button
#define IDOPT_ZALIGN 1042 // The z-align button
#define IDOPT_IVISFORM 1043 // iViS engine form
#define IDOPT_IVISLABEL 1044 // iViS form label
#define IDOPT_IVISSHADERS 1045 // iViS shaders button
#define IDOPT_IVISLIGHTING 1046 // iViS lighting button
/* Edit screen IDs */
#define IDED_FORM 2000 // The edit form
@ -1456,6 +1461,39 @@ static void intProcessOptions(UDWORD id)
intMode = INT_NORMAL;
// widgSetButtonState(psWScreen, IDRET_OPTIONS, 0);
break;
case IDOPT_IVISSHADERS:
{
bool status = pie_GetShadersStatus();
pie_SetShadersStatus(!status);
if (status != pie_GetShadersStatus())
{
if (!status)
{
widgSetButtonState(psWScreen, IDOPT_IVISSHADERS, WBUT_CLICKLOCK);
}
else
{
widgSetButtonState(psWScreen, IDOPT_IVISSHADERS, 0);
}
}
else
{
widgSetButtonState(psWScreen, IDOPT_IVISSHADERS, WBUT_DISABLE);
}
}
break;
case IDOPT_IVISLIGHTING:
if (pie_GetLightingState())
{
pie_SetLightingState(false);
widgSetButtonState(psWScreen, IDOPT_IVISLIGHTING, 0);
}
else
{
pie_SetLightingState(true);
widgSetButtonState(psWScreen, IDOPT_IVISLIGHTING, WBUT_CLICKLOCK);
}
break;
/* Ignore these */
case IDOPT_FORM:
case IDOPT_LABEL:
@ -1463,6 +1501,8 @@ static void intProcessOptions(UDWORD id)
case IDOPT_MAPLABEL:
case IDOPT_PLAYERFORM:
case IDOPT_PLAYERLABEL:
case IDOPT_IVISFORM:
case IDOPT_IVISLABEL:
break;
default:
ASSERT( false, "intProcessOptions: Unknown return code" );
@ -4173,6 +4213,70 @@ BOOL intAddOptions(void)
}
}
/* Add iViS form */
sFormInit.formID = IDOPT_FORM;
sFormInit.id = IDOPT_IVISFORM;
sFormInit.style = WFORM_PLAIN;
sFormInit.x = OPT_GAP;
sFormInit.y = OPT_PLAYERY + OPT_BUTHEIGHT * 3 + OPT_GAP * 5;
sFormInit.width = OPT_WIDTH - OPT_GAP * 2;
sFormInit.height = OPT_BUTHEIGHT * 3 + OPT_GAP * 4;
if (!widgAddForm(psWScreen, &sFormInit))
{
return false;
}
/* Add iViS label */
sLabInit.formID = IDOPT_IVISFORM;
sLabInit.id = IDOPT_IVISLABEL;
sLabInit.style = WLAB_PLAIN;
sLabInit.x = OPT_GAP;
sLabInit.y = OPT_GAP;
sLabInit.pText = "iViS:";
sLabInit.FontID = font_regular;
if (!widgAddLabel(psWScreen, &sLabInit))
{
return false;
}
/* Add iViS shaders button */
sButInit.formID = IDOPT_IVISFORM;
sButInit.id = IDOPT_IVISSHADERS;
sButInit.x = OPT_BUTWIDTH + OPT_GAP * 2;
sButInit.y = OPT_GAP;
sButInit.width = OPT_BUTWIDTH;
sButInit.height = OPT_BUTHEIGHT;
sButInit.FontID = font_regular;
sButInit.pText = "Shaders";
sButInit.pTip = "Toggles Shaders/FF mode.";
if (!widgAddButton(psWScreen, &sButInit))
{
return false;
}
if (pie_GetShadersStatus())
{
widgSetButtonState(psWScreen, IDOPT_IVISSHADERS, WBUT_CLICKLOCK);
}
/* Add iViS lighting button */
sButInit.formID = IDOPT_IVISFORM;
sButInit.id = IDOPT_IVISLIGHTING;
sButInit.x += OPT_BUTWIDTH + OPT_GAP;
sButInit.y = OPT_GAP;
sButInit.width = OPT_BUTWIDTH;
sButInit.height = OPT_BUTHEIGHT;
sButInit.FontID = font_regular;
sButInit.pText = "Lighting";
sButInit.pTip = "Toggles lighting On/Off.";
if (!widgAddButton(psWScreen, &sButInit))
{
return false;
}
if (pie_GetLightingState())
{
widgSetButtonState(psWScreen, IDOPT_IVISLIGHTING, WBUT_CLICKLOCK);
}
// widgStartScreen(psWScreen);
widgSetButtonState(psWScreen, IDOPT_PLAYERSTART + selectedPlayer, WBUT_LOCK);

View File

@ -23,32 +23,21 @@
* alexl.
*/
// ////////////////////////////////////////////////////////////////////////////
// includes
#include <string.h>
#include <SDL.h>
#include <physfs.h>
#include "lib/framework/frame.h"
#include "lib/framework/strres.h"
#include "lib/framework/input.h"
#include "lib/ivis_common/bitimage.h"
#include "lib/ivis_common/pieblitfunc.h"
#include "lib/sound/audio.h"
#include "lib/sound/audio_id.h"
#include "lib/widget/widget.h"
#include "frontend.h"
#include "frend.h"
#include "lib/ivis_common/textdraw.h"
#include "lib/ivis_common/piepalette.h"
#include "frontend.h"
#include "hci.h"
#include "init.h"
#include "loadsave.h"
#include "keymap.h"
#include "intimage.h"
#include "lib/ivis_common/bitimage.h"
#include "intdisplay.h"
#include "lib/sound/audio_id.h"
#include "lib/ivis_common/pieblitfunc.h"
#include "lib/netplay/netplay.h"
#include "keyedit.h"
#include "keymap.h"
#include "loadsave.h"
#include "main.h"
#include "multiint.h"
// ////////////////////////////////////////////////////////////////////////////
@ -67,9 +56,6 @@
#define KM_X 30
#define KM_Y 20
#define KM_RETURNX (KM_W-90)
#define KM_RETURNY (KM_H-42)
#define BUTTONSPERKEYMAPPAGE 20
#define KM_ENTRYW 480
@ -80,19 +66,7 @@
// variables
static KEY_MAPPING *selectedKeyMap;
// ////////////////////////////////////////////////////////////////////////////
// protos
BOOL runKeyMapEditor (void);
static BOOL keyMapToString (char *pStr, KEY_MAPPING *psMapping);
static void displayKeyMap(WIDGET *psWidget, UDWORD xOffset, UDWORD yOffset, PIELIGHT *pColours);
BOOL startKeyMapEditor (BOOL first);
BOOL saveKeyMap (void);
BOOL loadKeyMap (void);
static BOOL pushedKeyMap (UDWORD key);
char keymapVersion[8] = "KM_0002";
extern char KeyMapPath[];
static char keymapVersion[8] = "KM_0002";
// ////////////////////////////////////////////////////////////////////////////
// funcs
@ -318,7 +292,7 @@ static BOOL keyMapToString(char *pStr, KEY_MAPPING *psMapping)
// ////////////////////////////////////////////////////////////////////////////
// display a keymap on the interface.
void displayKeyMap(WIDGET *psWidget, UDWORD xOffset, UDWORD yOffset, WZ_DECL_UNUSED PIELIGHT *pColours)
static void displayKeyMap(WIDGET *psWidget, UDWORD xOffset, UDWORD yOffset, WZ_DECL_UNUSED PIELIGHT *pColours)
{
UDWORD x = xOffset+psWidget->x;
UDWORD y = yOffset+psWidget->y;

View File

@ -26,10 +26,10 @@ extern "C"
{
#endif //__cplusplus
extern BOOL runKeyMapEditor (void);
extern BOOL startKeyMapEditor (BOOL first);
extern BOOL saveKeyMap (void);
extern BOOL loadKeyMap (void);
BOOL runKeyMapEditor(void);
BOOL startKeyMapEditor(BOOL first);
BOOL saveKeyMap(void);
BOOL loadKeyMap(void);
#ifdef __cplusplus
}

View File

@ -42,6 +42,7 @@ extern void SetGameMode(GS_GAMEMODE status);
extern char SaveGamePath[PATH_MAX];
extern char datadir[PATH_MAX];
extern char configdir[PATH_MAX];
extern char KeyMapPath[PATH_MAX];
#define MAX_MODS 100

View File

@ -24,6 +24,7 @@
#ifndef __INCLUDED_SRC_MULTIINT_H__
#define __INCLUDED_SRC_MULTIINT_H__
#include "lib/netplay/netplay.h"
#include "lib/widget/widgbase.h"
#ifdef __cplusplus