extern "C" { #include "3dc.h" #include "inline.h" #include "module.h" #include "gamedef.h" #include "stratdef.h" #include "vramtime.h" #include "dxlog.h" #include "d3_func.h" #include "d3dmacs.h" #include "string.h" #include "kshape.h" #include "frustrum.h" #include "d3d_hud.h" #include "gamedef.h" #include "particle.h" #define UseLocalAssert No #include "ourasert.h" extern "C++"{ #include "r2base.h" #include // for sqrt }; #include "HUD_layout.h" #define HAVE_VISION_H 1 #include "vision.h" #include "lighting.h" #include "showcmds.h" #include "frustrum.h" #include "smacker.h" #include "d3d_render.h" #include "avp_userprofile.h" #include "bh_types.h" #include #define RGBLIGHT_MAKE(r,g,b) RGB_MAKE(r,g,b) #define RGBALIGHT_MAKE(r,g,b,a) RGBA_MAKE(r,g,b,a) // Set to Yes to make default texture filter bilinear averaging rather // than nearest extern BOOL BilinearTextureFilter; #define FMV_ON 0 #define FMV_EVERYWHERE 0 #define WIBBLY_FMV_ON 0 #define FMV_SIZE 128 VECTORCH FmvPosition = {42985-3500,2765-5000,-35457}; #define FOG_ON 0 #if 1 #define FOG_COLOUR 0x7f7f7f //0x404040 #define FOG_SCALE 512 #else #define FOG_COLOUR 0x7f7f7f//0xd282828 //0x404040 #define FOG_SCALE 256 #endif #define TriangleVertices 3 #define LineVertices 2 #define DefaultVertexIntensity 200 #define TransparentAlphaValue 128 #define DefaultColour (RGBLIGHT_MAKE(DefaultVertexIntensity,DefaultVertexIntensity,DefaultVertexIntensity)) #define DefaultAlphaColour (RGBALIGHT_MAKE(DefaultVertexIntensity,DefaultVertexIntensity,DefaultVertexIntensity,TransparentAlphaValue)) #if 0 #define TxIntensityLShift 4 #else #define TxIntensityLShift 0 #endif #define TxIntensityLimit 255 #define MaxVerticesInExecuteBuffer (MaxD3DVertices) // Colour is a 24-bit RGB colour, standard engine // internal format. // a is an 8 bit alpha value. #define MAKE_ALPHACOLOUR(colour, a) ((D3DCOLOR) (((a) << 24) | (colour))) extern int SpecialFXImageNumber; extern int SmokyImageNumber; extern int ChromeImageNumber; extern int HUDFontsImageNumber; extern int BurningImageNumber; extern int PredatorVisionChangeImageNumber; extern int PredatorNumbersImageNumber; extern int StaticImageNumber; extern int AAFontImageNumber; extern int WaterShaftImageNumber; D3DTEXTUREHANDLE FMVTextureHandle[4]; D3DTEXTUREHANDLE NoiseTextureHandle; int LightIntensityAtPoint(VECTORCH *pointPtr); // Externs extern int VideoMode; extern int WindowMode; extern int ScanDrawMode; extern int DXMemoryMode; extern int ZBufferRequestMode; extern int RasterisationRequestMode; extern int SoftwareScanDrawRequestMode; extern SCREENDESCRIPTORBLOCK ScreenDescriptorBlock; extern VIEWDESCRIPTORBLOCK* Global_VDB_Ptr; extern IMAGEHEADER ImageHeaderArray[]; extern int NumImagesArray[]; extern LPDIRECTDRAW lpDD; extern LPDIRECTDRAWSURFACE lpDDSPrimary; extern BOOL MMXAvailable; extern int NormalFrameTime; int WireFrameMode; extern int HUDScaleFactor; //Globals int D3DDriverMode; int NumVertices; static LPVOID ExecuteBufferDataArea; static LPVOID ExecuteBufferInstArea; static LPVOID ExecBufDataPtr; static LPVOID ExecBufInstPtr; static LPVOID ExecBufStartInstPtr; #if SupportZBuffering #endif static unsigned char D3DShadingMode; static unsigned char D3DTexturePerspective; static unsigned char D3DTBlendMode; static unsigned char D3DAlphaMode; static D3DTEXTUREHANDLE CurrTextureHandle; static unsigned char DefaultD3DTextureFilterMin; static unsigned char DefaultD3DTextureFilterMax; // Globals for frame by frame definition of // coloured materials for D3D rendering interface static int NumberOfRenderedTriangles=0; int NumberOfLandscapePolygons; RENDERSTATES CurrentRenderStates; extern HRESULT LastError; void ChangeTranslucencyMode(enum TRANSLUCENCY_TYPE translucencyRequired); void ChangeFilteringMode(enum FILTERING_MODE_ID filteringRequired); #define CheckTranslucencyModeIsCorrect(x) \ if (CurrentRenderStates.TranslucencyMode!=(x)) \ ChangeTranslucencyMode((x)); #define CheckFilteringModeIsCorrect(x) \ if (CurrentRenderStates.FilteringMode!=(x)) \ ChangeFilteringMode((x)); extern D3DINFO d3d; extern int ExBufSize; extern LPDIRECT3DEXECUTEBUFFER lpD3DExecCmdBuf; /* KJL 15:12:02 10/05/98 - FMV stuff */ static PALETTEENTRY FMVPalette[4][256]; void D3D_DrawFMVOnWater(int xOrigin, int yOrigin, int zOrigin); static void UpdateFMVTextures(int maxTextureNumberToUpdate); extern int NextFMVFrame(void*bufferPtr, int x, int y, int w, int h, int fmvNumber); extern void UpdateFMVPalette(PALETTEENTRY *FMVPalette, int fmvNumber); void D3D_DrawFMV(int xOrigin, int yOrigin, int zOrigin); VECTORCH FMVParticleAbsPosition[450]; VECTORCH FMVParticlePosition[450]; int FMVParticleColour; void D3D_DrawSwirlyFMV(int xOrigin, int yOrigin, int zOrigin); void D3D_FMVParticle_Output(RENDERVERTEX *renderVerticesPtr); void DrawFBM(void); void D3D_DrawCable(VECTORCH *centrePtr, MATRIXCH *orientationPtr); int WaterXOrigin; int WaterZOrigin; float WaterUScale; float WaterVScale; BOOL SetExecuteBufferDefaults(void) { D3DEXECUTEBUFFERDESC d3dexDesc; D3DEXECUTEDATA d3dExecData; memset(&d3dexDesc, 0, sizeof(D3DEXECUTEBUFFERDESC)); d3dexDesc.dwSize = sizeof(D3DEXECUTEBUFFERDESC); // Acquire lock on execute buffer LastError = lpD3DExecCmdBuf->Lock(&d3dexDesc); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; // Zero buffer and acquire pointers to start of areas memset(d3dexDesc.lpData, 0, ExBufSize); // Initialise pointers to data areas within buffer ExecuteBufferDataArea = d3dexDesc.lpData; ExecuteBufferInstArea = (LPVOID) ((int) ExecuteBufferDataArea + (int) (sizeof(D3DTLVERTEX) * MaxVerticesInExecuteBuffer)); ExecBufDataPtr = ExecuteBufferDataArea; ExecBufInstPtr = ExecuteBufferInstArea; NumVertices = 0; // If we can, we want to turn off culling at the level of the rasterisation // module. Note that Microsoft's software renderers do not support this, // unfortunately. #if 1 if (ScanDrawMode == ScanDrawD3DHardwareRGB) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_CULLMODE, D3DCULL_NONE, ExecBufInstPtr); } #endif #if SupportZBuffering OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZENABLE, TRUE, ExecBufInstPtr); // Certainly necess for new mixed HSR model!!! OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); #endif // Set default alpha modes with blending off OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND, D3DBLEND_SRCALPHA, ExecBufInstPtr); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND, D3DBLEND_INVSRCALPHA, ExecBufInstPtr); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, FALSE, ExecBufInstPtr); #if FOG_ON OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGENABLE, TRUE, ExecBufInstPtr); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGCOLOR, FOG_COLOUR, ExecBufInstPtr); #endif #if 0 { float fogStart = 2000.0f; // these values work on a Voodoo2, but not a G200. Hmm. float fogEnd = 32000.0f; OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGENABLE, TRUE, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGCOLOR, 0x7f7f7f, ExecBufInstPtr); #if 1 OP_STATE_RENDER(3, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGTABLEMODE, D3DFOG_LINEAR, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGTABLESTART, *(DWORD*)(&fogStart), ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FOGTABLEEND, *(DWORD*)(&fogEnd), ExecBufInstPtr); #endif // STATE_DATA(D3DRENDERSTATE_SPECULARENABLE, FALSE, ExecBufInstPtr); } #endif OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMAPBLEND, D3DTBLEND_MODULATE, ExecBufInstPtr); OP_EXIT(ExecBufInstPtr); // Unlock buffer LastError = lpD3DExecCmdBuf->Unlock(); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; // Setup for execution memset(&d3dExecData, 0, sizeof(D3DEXECUTEDATA)); d3dExecData.dwSize = sizeof(D3DEXECUTEDATA); // Vertices start at beginning of buffer, i.e. // at ExecuteBufferDataArea, so there is no // Vertex Offset. d3dExecData.dwVertexCount = NumVertices; d3dExecData.dwInstructionOffset = (ULONG) ((char*) ExecuteBufferInstArea - (char*) ExecuteBufferDataArea); d3dExecData.dwInstructionLength = (ULONG) ((char*)ExecBufInstPtr - (char*) ExecuteBufferInstArea); // Do the actual set up LastError = lpD3DExecCmdBuf->SetExecuteData(&d3dExecData); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; LastError = d3d.lpD3DDevice->BeginScene(); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; // Execute buffer // We will specify no clipping since the engine // already clips to the VDB. Eventually we might // try for no culling as well...if we're feeling // really daring... LastError = d3d.lpD3DDevice->Execute(lpD3DExecCmdBuf, d3d.lpD3DViewport, D3DEXECUTE_UNCLIPPED); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; // End scene LastError = d3d.lpD3DDevice->EndScene(); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; return TRUE; } static int NeedToClearExecuteBuffer=1; BOOL LockExecuteBuffer(void) { D3DEXECUTEBUFFERDESC d3dexDesc; memset(&d3dexDesc, 0, sizeof(D3DEXECUTEBUFFERDESC)); d3dexDesc.dwSize = sizeof(D3DEXECUTEBUFFERDESC); // Acquire lock on execute buffer LastError = lpD3DExecCmdBuf->Lock(&d3dexDesc); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; // Zero buffer and acquire pointers to start of areas // memset(d3dexDesc.lpData, 0, ExBufSize); // if(NeedToClearExecuteBuffer) { memset(d3dexDesc.lpData, 0, ExBufSize); // NeedToClearExecuteBuffer=0; } //textprint("ExBufSize %d %d %d %d\n",ExBufSize,sizeof(D3DINSTRUCTION),sizeof(D3DTRIANGLE),sizeof(D3DTLVERTEX) ); // Two lines below should really be in init routine, // but are here for the moment in case locking has // weird side effects. // FIXME!!!! // Initialise pointers to data areas within buffer ExecuteBufferDataArea = d3dexDesc.lpData; // Hmmm.... ExecuteBufferInstArea = (LPVOID) ((int) ExecuteBufferDataArea + (int) (sizeof(D3DTLVERTEX) * MaxVerticesInExecuteBuffer)); ExecBufDataPtr = ExecuteBufferDataArea; ExecBufInstPtr = ExecuteBufferInstArea; NumVertices = 0; // Force initialisation of render states during // first call to Write functions D3DShadingMode = 0xff; D3DTexturePerspective = 0xff; D3DAlphaMode = 0xff; // Other initialisations CurrTextureHandle = (D3DTEXTUREHANDLE) 0xff; // Save pointer to execute buffer and // wind that pointer on by the // amount of a process vertices data opcode and // associated data ExecBufStartInstPtr = ExecBufInstPtr; ExecBufInstPtr = (void*)(((LPD3DINSTRUCTION) ExecBufInstPtr) + 1); ExecBufInstPtr = (void*)(((LPD3DPROCESSVERTICES) ExecBufInstPtr) + 1); #if 0 // Set default texture filter for this frame // NOTE THAT BILINEAR BEHAVIOUR MIGHT EVENTUALLY BE BEST // MOVED TO AN ITEM FLAG, NOT A COMPILE OPTION // Note at present no support for averaging between // mip-maps!!! May well not exist on all (or most) accelerators // anyway!!! if (BilinearTextureFilter) { if (ScreenDescriptorBlock.SDB_Flags & SDB_Flag_MIP) { DefaultD3DTextureFilterMin = D3DFILTER_MIPLINEAR; DefaultD3DTextureFilterMax = D3DFILTER_MIPLINEAR; } else { DefaultD3DTextureFilterMin = D3DFILTER_LINEAR; DefaultD3DTextureFilterMax = D3DFILTER_LINEAR; } } else { if (ScreenDescriptorBlock.SDB_Flags & SDB_Flag_MIP) { DefaultD3DTextureFilterMin = D3DFILTER_MIPNEAREST; DefaultD3DTextureFilterMax = D3DFILTER_MIPNEAREST; } else { DefaultD3DTextureFilterMin = D3DFILTER_NEAREST; DefaultD3DTextureFilterMax = D3DFILTER_NEAREST; } } // Actually set default texture filters OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMAG, DefaultD3DTextureFilterMax, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMIN, DefaultD3DTextureFilterMin, ExecBufInstPtr); #endif return TRUE; } BOOL UnlockExecuteBufferAndPrepareForUse(void) { D3DEXECUTEDATA d3dExecData; // Unlock buffer LastError = lpD3DExecCmdBuf->Unlock(); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; // Setup for execution memset(&d3dExecData, 0, sizeof(D3DEXECUTEDATA)); d3dExecData.dwSize = sizeof(D3DEXECUTEDATA); // Vertices start at beginning of buffer, i.e. // at ExecuteBufferDataArea, so there is no // Vertex Offset. d3dExecData.dwVertexCount = NumVertices; d3dExecData.dwInstructionOffset = (ULONG) ((char*) ExecuteBufferInstArea - (char*) ExecuteBufferDataArea); d3dExecData.dwInstructionLength = (ULONG) ((char*)ExecBufInstPtr - (char*) ExecuteBufferInstArea); // Do the actual set up LastError = lpD3DExecCmdBuf->SetExecuteData(&d3dExecData); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; return TRUE; } // Test for multiple execute buffers!!!! BOOL BeginD3DScene(void) { #if SOFTWARE_RENDERER LockSurfaceAndGetBufferPointer(); return TRUE; #else NumberOfRenderedTriangles=0; LastError = d3d.lpD3DDevice->BeginScene(); LOGDXERR(LastError); if (LastError != D3D_OK) return FALSE; else return TRUE; #endif } void D3D_SetupSceneDefaults(void) { /* force translucency state to be reset */ CurrentRenderStates.TranslucencyMode = TRANSLUCENCY_NOT_SET; CurrentRenderStates.FilteringMode = FILTERING_NOT_SET; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); CheckWireFrameMode(0); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DITHERENABLE, TRUE, ExecBufInstPtr); } BOOL EndD3DScene(void) { #if SOFTWARE_RENDERER UnlockSurface(); return TRUE; #else extern int NormalFrameTime; LastError = d3d.lpD3DDevice->EndScene(); LOGDXERR(LastError); if (ShowDebuggingText.PolyCount) { ReleasePrintDebuggingText("NumberOfLandscapePolygons: %d\n",NumberOfLandscapePolygons); ReleasePrintDebuggingText("NumberOfRenderedTriangles: %d\n",NumberOfRenderedTriangles); } // textprint ("NumberOfRenderedTrianglesPerSecond: %d\n",DIV_FIXED(NumberOfRenderedTriangles,NormalFrameTime)); NumberOfLandscapePolygons=0; if (LastError != D3D_OK) return FALSE; else return TRUE; #endif } void WriteEndCodeToExecuteBuffer(void) { // Initialise execute buffer by specifying // that all operations will be rasterisation // only (this optimises the immediate mode interface // behaviour, since it knows that it will not // be asked to perform geometry transformations // or lighting operations). // Write process vertices instruction // to the START of the execute buffer, // now that we know how many vertices // there are. OP_PROCESS_VERTICES(1, ExecBufStartInstPtr); PROCESSVERTICES_DATA(D3DPROCESSVERTICES_COPY, 0, NumVertices, ExecBufStartInstPtr); // Write single termination opcode to buffer OP_EXIT(ExecBufInstPtr); } #include "pentime.h" BOOL ExecuteBuffer(void) { #if SOFTWARE_RENDERER return TRUE; #else // textprint("%d\n",sizeof(D3DINSTRUCTION) + sizeof(D3DTRIANGLE)); // textprint("NumVertices %d\n Instructions %d",NumVertices,(char*)ExecBufInstPtr-(char*)ExecBufStartInstPtr); //ProfileStart(); LastError = d3d.lpD3DDevice->Execute(lpD3DExecCmdBuf, d3d.lpD3DViewport, D3DEXECUTE_UNCLIPPED); LOGDXERR(LastError); //ProfileStop("execute buffer"); if (LastError != D3D_OK) return FALSE; else return TRUE; #endif } void CheckRenderStatesForModule(MODULE *modulePtr) { // textprint("fog %d\n",CurrentRenderStates.FogIsOn); if (modulePtr->m_flags & MODULEFLAG_FOG) { // CurrentRenderStates.FogIsOn = 1; } else { // CurrentRenderStates.FogIsOn = 0; } } void SetFogDistance(int fogDistance) { if (fogDistance>10000) fogDistance = 10000; fogDistance+=5000; fogDistance=2000; CurrentRenderStates.FogDistance = fogDistance; // textprint("fog distance %d\n",fogDistance); } void ChangeTranslucencyMode(enum TRANSLUCENCY_TYPE translucencyRequired) { // OP_STATE_RENDER(1, ExecBufInstPtr); // STATE_DATA(D3DRENDERSTATE_STIPPLEDALPHA,FALSE, ExecBufInstPtr); // OP_STATE_RENDER(1, ExecBufInstPtr); // STATE_DATA(D3DRENDERSTATE_STIPPLEENABLE,FALSE, ExecBufInstPtr); // if (CurrentRenderStates.TranslucencyMode!=(translucencyRequired)) { CurrentRenderStates.TranslucencyMode=translucencyRequired; switch(CurrentRenderStates.TranslucencyMode) { case TRANSLUCENCY_OFF: { if (TRIPTASTIC_CHEATMODE||MOTIONBLUR_CHEATMODE) { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_INVSRCALPHA, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_SRCALPHA, ExecBufInstPtr); } else { if (D3DAlphaMode != No) { D3DAlphaMode = No; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, FALSE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_ONE, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_ZERO, ExecBufInstPtr); } break; } case TRANSLUCENCY_NORMAL: { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_SRCALPHA, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_INVSRCALPHA, ExecBufInstPtr); break; } case TRANSLUCENCY_COLOUR: { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_ZERO, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_SRCCOLOR, ExecBufInstPtr); break; } case TRANSLUCENCY_INVCOLOUR: { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_ZERO, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_INVSRCCOLOR, ExecBufInstPtr); break; } case TRANSLUCENCY_GLOWING: { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_SRCALPHA, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_ONE, ExecBufInstPtr); break; } case TRANSLUCENCY_DARKENINGCOLOUR: { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_INVDESTCOLOR, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_ZERO, ExecBufInstPtr); break; } case TRANSLUCENCY_JUSTSETZ: { if (D3DAlphaMode != Yes) { D3DAlphaMode = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ALPHABLENDENABLE, TRUE, ExecBufInstPtr); } OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SRCBLEND,D3DBLEND_ZERO, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_DESTBLEND,D3DBLEND_ONE, ExecBufInstPtr); } default: break; } } } void ChangeFilteringMode(enum FILTERING_MODE_ID filteringRequired) { CurrentRenderStates.FilteringMode = filteringRequired; switch(CurrentRenderStates.FilteringMode) { case FILTERING_BILINEAR_OFF: { OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMAG, D3DFILTER_NEAREST, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMIN, D3DFILTER_NEAREST, ExecBufInstPtr); break; } case FILTERING_BILINEAR_ON: { OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMAG, D3DFILTER_LINEAR, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMIN, D3DFILTER_LINEAR, ExecBufInstPtr); break; } default: { LOCALASSERT("Unrecognized filtering mode"==0); break; } } } extern void CheckWireFrameMode(int shouldBeOn) { if (shouldBeOn) shouldBeOn=1; if(CurrentRenderStates.WireFrameModeIsOn!=shouldBeOn) { CurrentRenderStates.WireFrameModeIsOn=shouldBeOn; if (shouldBeOn) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FILLMODE, D3DFILL_WIREFRAME, ExecBufInstPtr); } else { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_FILLMODE, D3DFILL_SOLID, ExecBufInstPtr); } } } void D3D_Line(VECTOR2D* LineStart, VECTOR2D* LineEnd, int LineColour) { if (d3d.ThisDriver.dpcLineCaps.dwShadeCaps & D3DPSHADECAPS_COLORFLATRGB) { int x1, x2, y1, y2; D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; // Test!!! // LineColour = 0xffffffff; vertexPtr->sx = LineStart->vx; vertexPtr->sy = LineStart->vy; vertexPtr[1].sx = LineEnd->vx; vertexPtr[1].sy = LineEnd->vy; NumVertices+=2; vertexPtr->color = LineColour; vertexPtr[1].color = LineColour; // Always turn off translucency for the moment CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } OP_LINE_LIST(1, ExecBufInstPtr); ((LPD3DLINE)ExecBufInstPtr)->v1 = (NumVertices-2); // vertex index ((LPD3DLINE)ExecBufInstPtr)->v2 = (NumVertices-1); // vertex index ExecBufInstPtr = ((char*)ExecBufInstPtr) + sizeof(D3DLINE); } if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } static void D3D_OutputTriangles(void); void D3D_BackdropPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { int flags; int texoffset; D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); // Take header information flags = inputPolyPtr->PolyFlags; // We assume bit 15 (TxLocal) HAS been // properly cleared this time... texoffset = (inputPolyPtr->PolyColour & ClrTxDefn); TextureHandle = (D3DTEXTUREHANDLE) ImageHeaderArray[texoffset].D3DHandle; // Check for textures that have not loaded // properly if (TextureHandle == (D3DTEXTUREHANDLE) 0) return; if(ImageHeaderArray[texoffset].ImageWidth==128) { RecipW = 1.0 /128.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==128) { RecipH = 1.0 / 128.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } vertexPtr->tu = ((float)(vertices->U>>16)+.5) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)+.5) * RecipH; vertexPtr->rhw = oneOverZ; vertexPtr->color = RGBLIGHT_MAKE(vertices->R,vertices->G,vertices->B); vertexPtr->sz = 1.0; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,255); vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Insert state change for texturing perspective value // Note that drawtx3das2d options have ONLY been allowed for here, // not when the rhw values are generated. This is a deliberate choice, // based on the assumption that drawtx3das2d will not be used very often // and the extra branching at the top of this function will impose a // greater cost than the (rare) savings in floating pt divisions are worth. // Or so I claim... if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } D3D_OutputTriangles(); } void D3D_ZBufferedGouraudTexturedPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { int flags; int texoffset; D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); // Take header information flags = inputPolyPtr->PolyFlags; // We assume bit 15 (TxLocal) HAS been // properly cleared this time... texoffset = (inputPolyPtr->PolyColour & ClrTxDefn); if (texoffset) { TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[texoffset].D3DHandle; } else { TextureHandle = CurrTextureHandle; } // Check for textures that have not loaded // properly // if (TextureHandle == (D3DTEXTUREHANDLE) 0) // return; #ifdef AVP_DEBUG_VERSION if(ImageHeaderArray[texoffset].ImageWidth==128) { RecipW = (1.0f /128.0f)/65536.0f; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0f / width)/65536.0f; } if(ImageHeaderArray[texoffset].ImageHeight==128) { RecipH = (1.0f / 128.0f)/65536.0f; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0f / height)/65536.0f; } #else RecipW = (1.0f/65536.0f)/128.0f; RecipH = (1.0f/65536.0f)/128.0f; #endif // RecipW = (1.0/65536.0)/(float) ImageHeaderArray[texoffset].ImageWidth; // RecipH = (1.0/65536.0)/(float) ImageHeaderArray[texoffset].ImageHeight; /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0f)/(vertices->Z); float zvalue; vertexPtr->tu = ((float)vertices->U) * RecipW + (1.0f/256.0f); vertexPtr->tv = ((float)vertices->V) * RecipH + (1.0f/256.0f); vertexPtr->rhw = oneOverZ; { zvalue = vertices->Z+HeadUpDisplayZOffset; // zvalue /= 65536.0; zvalue = 1.0f - ZNear/zvalue; } { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; #if 1 if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } #endif vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; #if 1 if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } #endif vertexPtr->sy=y; } // vertexPtr->tu = ((float)(vertices->U>>16)+0.5) * RecipW; // vertexPtr->tv = ((float)(vertices->V>>16)+0.5) * RecipH; // vertexPtr->rhw = oneOverZ; { extern unsigned char GammaValues[256]; vertexPtr->color = RGBALIGHT_MAKE(GammaValues[vertices->R],GammaValues[vertices->G],GammaValues[vertices->B],vertices->A); } vertexPtr->sz = zvalue; #if 0//FOG_ON { extern unsigned char GammaValues[256]; int r = GammaValues[vertices->SpecularR]; int g = GammaValues[vertices->SpecularG]; int b = GammaValues[vertices->SpecularB]; if(CurrentRenderStates.FogIsOn && vertices->Z>5000)//CurrentRenderStates.FogDistance) { // extern int CloakingPhase; int brightness = (vertices->R+vertices->G+vertices->B)*86*3; int fog = ((vertices->Z-5000/*-CurrentRenderStates.FogDistance*/)*4); if (fog<0) fog=0; if (fog>brightness) fog = brightness; if (fog>ONE_FIXED) fog=ONE_FIXED; { extern int SkyColour_R; int rfog = MUL_FIXED(fog,SkyColour_R); if (rspecular=RGBALIGHT_MAKE(r,g,b,255); } #else #if 0 if (RenderPolygon.TranslucencyMode != TRANSLUCENCY_OFF) { vertexPtr->specular=0; } else #endif { extern unsigned char GammaValues[256]; vertexPtr->specular=RGBALIGHT_MAKE(GammaValues[vertices->SpecularR],GammaValues[vertices->SpecularG],GammaValues[vertices->SpecularB],255); } #endif vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(RenderPolygon.TranslucencyMode); // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Insert state change for texturing perspective value // Note that drawtx3das2d options have ONLY been allowed for here, // not when the rhw values are generated. This is a deliberate choice, // based on the assumption that drawtx3das2d will not be used very often // and the extra branching at the top of this function will impose a // greater cost than the (rare) savings in floating pt divisions are worth. // Or so I claim... if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } #if FMV_EVERYWHERE TextureHandle = FMVTextureHandle[0]; #endif if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } D3D_OutputTriangles(); } void D3D_ZBufferedGouraudPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { int flags; float ZNear; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); // Take header information flags = inputPolyPtr->PolyFlags; /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } { zvalue = vertices->Z+HeadUpDisplayZOffset; zvalue = ((zvalue-ZNear)/zvalue); } { if (flags & iflag_transparent) { vertexPtr->color = RGBALIGHT_MAKE(vertices->R,vertices->G,vertices->B, vertices->A); } else { vertexPtr->color = RGBLIGHT_MAKE(vertices->R,vertices->G,vertices->B); } } vertexPtr->sz = zvalue; vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(RenderPolygon.TranslucencyMode); // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } D3D_OutputTriangles(); } void D3D_PredatorThermalVisionPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { float ZNear; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } { zvalue = vertices->Z+HeadUpDisplayZOffset; zvalue = ((zvalue-ZNear)/zvalue); } vertexPtr->color = RGBALIGHT_MAKE(vertices->R,vertices->G,vertices->B,vertices->A);//RGBALIGHT_MAKE(255,255,255,255); vertexPtr->sz = zvalue; vertexPtr->rhw = zvalue; vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } D3D_OutputTriangles(); } void D3D_PredatorSeeAliensVisionPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { float ZNear; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } { zvalue = vertices->Z+HeadUpDisplayZOffset; zvalue = ((zvalue-ZNear)/zvalue); } vertexPtr->color = RGBALIGHT_MAKE(255,0,0,255);//255,255,255,255); vertexPtr->sz = zvalue; vertexPtr->rhw = zvalue; vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING)//JUSTSETZ); // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } D3D_OutputTriangles(); } void D3D_ZBufferedCloakedPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { extern int CloakingMode; extern char CloakedPredatorIsMoving; int uOffset = FastRandom()&255; int vOffset = FastRandom()&255; int flags; int texoffset; D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); // Take header information flags = inputPolyPtr->PolyFlags; // We assume bit 15 (TxLocal) HAS been // properly cleared this time... texoffset = (inputPolyPtr->PolyColour & ClrTxDefn); TextureHandle = (D3DTEXTUREHANDLE) ImageHeaderArray[texoffset].D3DHandle; // Check for textures that have not loaded // properly if (TextureHandle == (D3DTEXTUREHANDLE) 0) return; if(ImageHeaderArray[texoffset].ImageWidth==128) { RecipW = 1.0 /128.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==128) { RecipH = 1.0 / 128.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } vertexPtr->tu = ((float)(vertices->U>>16)+0.5) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)+0.5) * RecipH; if (CloakedPredatorIsMoving) { vertexPtr->color = RGBALIGHT_MAKE(vertices->R,vertices->G,vertices->B,vertices->A); } else { vertexPtr->color = RGBALIGHT_MAKE(vertices->R,vertices->G,vertices->B,vertices->A); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); vertexPtr->rhw = oneOverZ; { zvalue = vertices->Z+HeadUpDisplayZOffset; zvalue = ((zvalue-ZNear)/zvalue); } vertexPtr->sz = zvalue; // vertexPtr->specular=RGBALIGHT_MAKE(vertices->SpecularR,vertices->SpecularG,vertices->SpecularB,255); vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,255); vertices++; NumVertices++; } while(--i); } // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Insert state change for texturing perspective value // Note that drawtx3das2d options have ONLY been allowed for here, // not when the rhw values are generated. This is a deliberate choice, // based on the assumption that drawtx3das2d will not be used very often // and the extra branching at the top of this function will impose a // greater cost than the (rare) savings in floating pt divisions are worth. // Or so I claim... if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } /* if (TextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } */ D3D_OutputTriangles(); } void D3D_CloakedPredatorPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); int texoffset = SpecialFXImageNumber; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[texoffset].D3DHandle; float RecipW, RecipH; if(ImageHeaderArray[texoffset].ImageWidth==256) { RecipW = 1.0 /256.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==256) { RecipH = 1.0 / 256.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/(vertices->Z); float zvalue; vertexPtr->tu = ((float)vertices->U) * RecipW; vertexPtr->tv = ((float)vertices->V) * RecipH; vertexPtr->rhw = oneOverZ; { zvalue = vertices->Z+HeadUpDisplayZOffset; // zvalue /= 65536.0; zvalue = 1.0 - ZNear/zvalue; } { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; #if 1 if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } #endif vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; #if 1 if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } #endif vertexPtr->sy=y; } vertexPtr->color = RGBALIGHT_MAKE(255,255,255,32); vertexPtr->sz = zvalue; vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Insert state change for texturing perspective value // Note that drawtx3das2d options have ONLY been allowed for here, // not when the rhw values are generated. This is a deliberate choice, // based on the assumption that drawtx3das2d will not be used very often // and the extra branching at the top of this function will impose a // greater cost than the (rare) savings in floating pt divisions are worth. // Or so I claim... if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } #if 1 if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } #else if (CurrTextureHandle != NoiseTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NoiseTextureHandle, ExecBufInstPtr); CurrTextureHandle = NoiseTextureHandle; } #endif D3D_OutputTriangles(); } void D3D_ZBufferedTexturedPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { int flags; int texoffset; int intensity; D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); // Take header information flags = inputPolyPtr->PolyFlags; intensity = (inputPolyPtr->PolyColour >> TxDefn); intensity >>= TxDefn; // We assume bit 15 (TxLocal) HAS been // properly cleared this time... texoffset = (inputPolyPtr->PolyColour & ClrTxDefn); TextureHandle = (D3DTEXTUREHANDLE) ImageHeaderArray[texoffset].D3DHandle; // Check for textures that have not loaded // properly if (TextureHandle == (D3DTEXTUREHANDLE) 0) return; if(ImageHeaderArray[texoffset].ImageWidth==128) { RecipW = 1.0 /128.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==128) { RecipH = 1.0 / 128.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } vertexPtr->tu = ((float)(vertices->U>>16)+0.5) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)+0.5) * RecipH; vertexPtr->rhw = oneOverZ; { zvalue = vertices->Z+HeadUpDisplayZOffset; zvalue = ((zvalue-ZNear)/zvalue); } // Different behaviour for different driver modes switch (D3DDriverMode) { case D3DSoftwareRGBDriver: { if (flags & iflag_nolight) { vertexPtr->color = DefaultColour; } else { int i1shift = intensity; vertexPtr->color = RGBLIGHT_MAKE(i1shift, i1shift,i1shift); } break; } case D3DSoftwareRampDriver: { // Blue component only valid for ramp driver if (flags & iflag_nolight) { vertexPtr->color = RGB_MAKE(0,0,DefaultVertexIntensity); } else { vertexPtr->color = RGB_MAKE(0,0,intensity); } break; } case D3DHardwareRGBDriver: { if (flags & iflag_transparent) { if (flags & iflag_nolight) { vertexPtr->color = DefaultAlphaColour; } else { vertexPtr->color = RGBALIGHT_MAKE(intensity,intensity,intensity, TransparentAlphaValue); } } else { if (flags & iflag_nolight) { vertexPtr->color = DefaultColour; } else { vertexPtr->color = RGBLIGHT_MAKE(intensity,intensity,intensity); } } break; } default: { vertexPtr->color = 0; break; } } vertexPtr->sz = zvalue; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,255); vertices++; NumVertices++; } while(--i); } if (flags & iflag_transparent) { CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); } else { CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); } // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Insert state change for texturing perspective value // Note that drawtx3das2d options have ONLY been allowed for here, // not when the rhw values are generated. This is a deliberate choice, // based on the assumption that drawtx3das2d will not be used very often // and the extra branching at the top of this function will impose a // greater cost than the (rare) savings in floating pt divisions are worth. // Or so I claim... if ((flags & iflag_drawtx3das2d) || (Global_VDB_Ptr->VDB_Flags & ViewDB_Flag_drawtx3das2d)) { if (D3DTexturePerspective != No) { D3DTexturePerspective = No; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, FALSE, ExecBufInstPtr); } } else { if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } } if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } D3D_OutputTriangles(); } #define OUTPUT_TRIANGLE(a,b,c,n) \ ((LPD3DTRIANGLE)ExecBufInstPtr)->v1 = (NumVertices+(a)-(n)); \ ((LPD3DTRIANGLE)ExecBufInstPtr)->v2 = (NumVertices+(b)-(n)); \ ((LPD3DTRIANGLE)ExecBufInstPtr)->v3 = (NumVertices+(c)-(n)); \ ((LPD3DTRIANGLE)ExecBufInstPtr)->wFlags = D3DTRIFLAG_EDGEENABLETRIANGLE; \ ExecBufInstPtr = ((char*)ExecBufInstPtr) + sizeof(D3DTRIANGLE); \ NumberOfRenderedTriangles++; static void D3D_OutputTriangles(void) { #if 0 OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); #endif #if 0 /* KJL 18:17:54 24/02/98 - doesn't seem to make any difference! */ if (QWORD_ALIGNED(ExecBufInstPtr)) { OP_NOP(ExecBufInstPtr); } #endif switch(RenderPolygon.NumberOfVertices) { default: case 3: { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(0,2,1, 3); break; } case 4: { OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,2, 4); OUTPUT_TRIANGLE(0,2,3, 4); break; } case 5: { OP_TRIANGLE_LIST(3, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,4, 5); OUTPUT_TRIANGLE(1,3,4, 5); OUTPUT_TRIANGLE(1,2,3, 5); break; } case 6: { OP_TRIANGLE_LIST(4, ExecBufInstPtr); OUTPUT_TRIANGLE(0,4,5, 6); OUTPUT_TRIANGLE(0,3,4, 6); OUTPUT_TRIANGLE(0,2,3, 6); OUTPUT_TRIANGLE(0,1,2, 6); break; } case 7: { OP_TRIANGLE_LIST(5, ExecBufInstPtr); OUTPUT_TRIANGLE(0,5,6, 7); OUTPUT_TRIANGLE(0,4,5, 7); OUTPUT_TRIANGLE(0,3,4, 7); OUTPUT_TRIANGLE(0,2,3, 7); OUTPUT_TRIANGLE(0,1,2, 7); break; } case 8: { OP_TRIANGLE_LIST(6, ExecBufInstPtr); OUTPUT_TRIANGLE(0,6,7, 8); OUTPUT_TRIANGLE(0,5,6, 8); OUTPUT_TRIANGLE(0,4,5, 8); OUTPUT_TRIANGLE(0,3,4, 8); OUTPUT_TRIANGLE(0,2,3, 8); OUTPUT_TRIANGLE(0,1,2, 8); break; } } if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } void D3D_HUD_Setup(void) { CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); // turn off perspective drawing if (D3DTexturePerspective != No) { D3DTexturePerspective = No; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, FALSE, ExecBufInstPtr); } /* OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMAG, D3DFILTER_NEAREST, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMIN, D3DFILTER_NEAREST, ExecBufInstPtr); OP_STATE_RENDER(2, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMAG, DefaultD3DTextureFilterMax, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREMIN, DefaultD3DTextureFilterMin, ExecBufInstPtr); */ OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); } void D3D_HUDQuad_Output(int imageNumber,struct VertexTag *quadVerticesPtr, unsigned int colour) { float RecipW, RecipH; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[imageNumber].D3DHandle; // Check for textures that have not loaded properly LOCALASSERT(TextureHandle != (D3DTEXTUREHANDLE) 0); if(ImageHeaderArray[imageNumber].ImageWidth==128) { RecipW = 1.0f / 128.0f; } else { float width = (float) ImageHeaderArray[imageNumber].ImageWidth - 0.0f; RecipW = (1.0f / width); } if(ImageHeaderArray[imageNumber].ImageHeight==128) { RecipH = 1.0f / 128.0f; } else { float height = (float) ImageHeaderArray[imageNumber].ImageHeight - 0.0f; RecipH = (1.0f / height); } /* OUTPUT quadVerticesPtr TO EXECUTE BUFFER */ { int i = 4; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; // textprint("x %d, y %d, u %d, v %d\n",quadVerticesPtr->X,quadVerticesPtr->Y,quadVerticesPtr->U,quadVerticesPtr->V); vertexPtr->sx=quadVerticesPtr->X; vertexPtr->sy=quadVerticesPtr->Y; vertexPtr->tu = ((float)(quadVerticesPtr->U)) * RecipW; vertexPtr->tv = ((float)(quadVerticesPtr->V)) * RecipH; vertexPtr->rhw = 1.0f; vertexPtr->color = colour; vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); quadVerticesPtr++; NumVertices++; } while(--i); } // set correct texture handle if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); /* output triangles to execute buffer */ OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); /* check to see if buffer is getting full */ if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } void D3D_DrawRebellionLogo(unsigned int alpha) { extern int RebellionLogoImageNumber; extern int FoxLogoImageNumber; float scale = ScreenDescriptorBlock.SDB_Width/640.0f; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[FoxLogoImageNumber].D3DHandle; int colour = 0xffffff+((alpha>>8)<<24); // Check for textures that have not loaded properly LOCALASSERT(TextureHandle != (D3DTEXTUREHANDLE) 0); /* OUTPUT quadVerticesPtr TO EXECUTE BUFFER */ { float x[] = {0.0f,1.0f,1.0f,0.0f}; float y[] = {0.0f,0.0f,1.0f,1.0f}; int i; for (i=0; i<4; i++) { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = (x[i]*63.0f+64.0f)*scale; vertexPtr->sy = (y[i]*63.0f+4.0f)*scale; vertexPtr->sz = 0.0f; vertexPtr->tu = x[i]; vertexPtr->tv = y[i]; vertexPtr->rhw = 1.0; vertexPtr->color = colour; vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); NumVertices++; } } // set correct texture handle if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); /* output triangles to execute buffer */ OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); /* check to see if buffer is getting full */ if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[RebellionLogoImageNumber].D3DHandle; { float x[] = {0.0f,1.0f,1.0f,0.0f}; float y[] = {0.0f,0.0f,1.0f,1.0f}; int i; for (i=0; i<4; i++) { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = (x[i]*127.0f+4.0f+130.0f)*scale; vertexPtr->sy = (y[i]*63.0f+4.0f)*scale; vertexPtr->sz = 0.0f; vertexPtr->tu = x[i]; vertexPtr->tv = y[i]; vertexPtr->rhw = 1.0; vertexPtr->color = colour; vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); NumVertices++; } } // set correct texture handle if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); /* output triangles to execute buffer */ OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); /* check to see if buffer is getting full */ if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } void D3D_DrawParticle_Rain(PARTICLE *particlePtr,VECTORCH *prevPositionPtr) { VECTORCH vertices[3]; vertices[0] = *prevPositionPtr; /* translate second vertex into view space */ TranslatePointIntoViewspace(&vertices[0]); /* is particle within normal view frustrum ? */ if((-vertices[0].vx <= vertices[0].vz) &&(vertices[0].vx <= vertices[0].vz) &&(-vertices[0].vy <= vertices[0].vz) &&(vertices[0].vy <= vertices[0].vz)) { vertices[1] = particlePtr->Position; vertices[2] = particlePtr->Position; vertices[1].vx += particlePtr->Offset.vx; vertices[2].vx -= particlePtr->Offset.vx; vertices[1].vz += particlePtr->Offset.vz; vertices[2].vz -= particlePtr->Offset.vz; /* translate particle into view space */ TranslatePointIntoViewspace(&vertices[1]); TranslatePointIntoViewspace(&vertices[2]); float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = 3; VECTORCH *verticesPtr = vertices; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; int x = (verticesPtr->vx*(Global_VDB_Ptr->VDB_ProjX))/verticesPtr->vz+Global_VDB_Ptr->VDB_CentreX; int y = (verticesPtr->vy*(Global_VDB_Ptr->VDB_ProjY))/verticesPtr->vz+Global_VDB_Ptr->VDB_CentreY; { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } float oneOverZ = ((float)verticesPtr->vz-ZNear)/(float)verticesPtr->vz; if (i==3) vertexPtr->color = RGBALIGHT_MAKE(0,255,255,32); else vertexPtr->color = RGBALIGHT_MAKE(255,255,255,32); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr->sz = oneOverZ; NumVertices++; verticesPtr++; } while(--i); } if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(0,2,1, 3); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } } void D3D_DrawParticle_Smoke(PARTICLE *particlePtr) { VECTORCH vertices[3]; vertices[0] = particlePtr->Position; /* translate second vertex into view space */ TranslatePointIntoViewspace(&vertices[0]); /* is particle within normal view frustrum ? */ int inView = 0; if(AvP.PlayerType == I_Alien) { if((-vertices[0].vx <= vertices[0].vz*2) &&(vertices[0].vx <= vertices[0].vz*2) &&(-vertices[0].vy <= vertices[0].vz*2) &&(vertices[0].vy <= vertices[0].vz*2)) { inView = 1; } } else { if((-vertices[0].vx <= vertices[0].vz) &&(vertices[0].vx <= vertices[0].vz) &&(-vertices[0].vy <= vertices[0].vz) &&(vertices[0].vy <= vertices[0].vz)) { inView = 1; } } if (inView) { vertices[1] = particlePtr->Position; vertices[2] = particlePtr->Position; vertices[1].vx += ((FastRandom()&15)-8)*2; vertices[1].vy += ((FastRandom()&15)-8)*2; vertices[1].vz += ((FastRandom()&15)-8)*2; vertices[2].vx += ((FastRandom()&15)-8)*2; vertices[2].vy += ((FastRandom()&15)-8)*2; vertices[2].vz += ((FastRandom()&15)-8)*2; /* translate particle into view space */ TranslatePointIntoViewspace(&vertices[1]); TranslatePointIntoViewspace(&vertices[2]); float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = 3; VECTORCH *verticesPtr = vertices; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; int x = (verticesPtr->vx*(Global_VDB_Ptr->VDB_ProjX))/verticesPtr->vz+Global_VDB_Ptr->VDB_CentreX; int y = (verticesPtr->vy*(Global_VDB_Ptr->VDB_ProjY))/verticesPtr->vz+Global_VDB_Ptr->VDB_CentreY; { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } float zvalue = (vertices->vz)+HeadUpDisplayZOffset; zvalue = ((zvalue-ZNear)/zvalue); // Different behaviour for different driver modes switch (D3DDriverMode) { default: case D3DSoftwareRGBDriver: case D3DSoftwareRampDriver: break; case D3DHardwareRGBDriver: { vertexPtr->color = RGBALIGHT_MAKE((particlePtr->LifeTime>>8),(particlePtr->LifeTime>>8),0,(particlePtr->LifeTime>>7)+64); break; } } vertexPtr->sz = zvalue; NumVertices++; verticesPtr++; } while(--i); } OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(0,2,1, 3); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } } void D3D_DecalSystem_Setup(void) { #if 1 OP_STATE_RENDER(1, ExecBufInstPtr); // STATE_DATA(D3DRENDERSTATE_DITHERENABLE, FALSE, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); #endif } void D3D_DecalSystem_End(void) { #if 1 OP_STATE_RENDER(1, ExecBufInstPtr); // STATE_DATA(D3DRENDERSTATE_DITHERENABLE, TRUE, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); #endif } void D3D_Decal_Output(DECAL *decalPtr,RENDERVERTEX *renderVerticesPtr) { DECAL_DESC *decalDescPtr = &DecalDescription[decalPtr->DecalID]; int texoffset; D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; int colour; int specular=RGBALIGHT_MAKE(0,0,0,0);//255); // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); if (decalPtr->DecalID == DECAL_FMV) { #if !FMV_ON return; #endif TextureHandle=FMVTextureHandle[decalPtr->Centre.vx]; RecipW = 1.0 /128.0; RecipH = 1.0 /128.0; if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } } else if (decalPtr->DecalID == DECAL_SHAFTOFLIGHT||decalPtr->DecalID == DECAL_SHAFTOFLIGHT_OUTER) { if (NULL != CurrTextureHandle) { CurrTextureHandle = NULL; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); } } else { texoffset = SpecialFXImageNumber; TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[texoffset].D3DHandle; // Check for textures that have not loaded // properly if (TextureHandle == (D3DTEXTUREHANDLE) 0) return; if(ImageHeaderArray[texoffset].ImageWidth==256) { RecipW = 1.0 /256.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==256) { RecipH = 1.0 / 256.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } } if (decalDescPtr->IsLit) { int intensity = LightIntensityAtPoint(decalPtr->Vertices); colour = RGBALIGHT_MAKE ( MUL_FIXED(intensity,decalDescPtr->RedScale[CurrentVisionMode]), MUL_FIXED(intensity,decalDescPtr->GreenScale[CurrentVisionMode]), MUL_FIXED(intensity,decalDescPtr->BlueScale[CurrentVisionMode]), decalDescPtr->Alpha ); } else { colour = RGBALIGHT_MAKE ( decalDescPtr->RedScale[CurrentVisionMode], decalDescPtr->GreenScale[CurrentVisionMode], decalDescPtr->BlueScale[CurrentVisionMode], decalDescPtr->Alpha ); } if (RAINBOWBLOOD_CHEATMODE) { colour = RGBALIGHT_MAKE ( FastRandom()&255, FastRandom()&255, FastRandom()&255, decalDescPtr->Alpha ); } /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } vertexPtr->tu = ((float)(vertices->U>>16)+.5) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)+.5) * RecipH; vertexPtr->rhw = oneOverZ; { zvalue = (vertices->Z)+HeadUpDisplayZOffset-50; zvalue = ((zvalue-ZNear)/zvalue); } vertexPtr->color = colour; vertexPtr->sz = zvalue; vertexPtr->specular= specular;//RGBALIGHT_MAKE(vertices->SpecularR,vertices->SpecularG,vertices->SpecularB,fog); vertices++; NumVertices++; } while(--i); } /* Check translucency mode */ CheckTranslucencyModeIsCorrect(decalDescPtr->TranslucencyType); if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } D3D_OutputTriangles(); } void D3D_Particle_Output(PARTICLE *particlePtr,RENDERVERTEX *renderVerticesPtr) { #if 1 PARTICLE_DESC *particleDescPtr = &ParticleDescription[particlePtr->ParticleID]; int texoffset = SpecialFXImageNumber; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[texoffset].D3DHandle; float RecipW, RecipH; // Check for textures that have not loaded // properly if (TextureHandle == (D3DTEXTUREHANDLE) 0) return; if(ImageHeaderArray[texoffset].ImageWidth==256) { RecipW = 1.0 /256.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==256) { RecipH = 1.0 / 256.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } int colour; if (particleDescPtr->IsLit && !(particlePtr->ParticleID==PARTICLE_ALIEN_BLOOD && CurrentVisionMode==VISION_MODE_PRED_SEEALIENS) ) { int intensity = LightIntensityAtPoint(&particlePtr->Position); if (particlePtr->ParticleID==PARTICLE_SMOKECLOUD || particlePtr->ParticleID==PARTICLE_ANDROID_BLOOD) { colour = RGBALIGHT_MAKE ( MUL_FIXED(intensity,particlePtr->ColourComponents.Red), MUL_FIXED(intensity,particlePtr->ColourComponents.Green), MUL_FIXED(intensity,particlePtr->ColourComponents.Blue), particlePtr->ColourComponents.Alpha ); } else { colour = RGBALIGHT_MAKE ( MUL_FIXED(intensity,particleDescPtr->RedScale[CurrentVisionMode]), MUL_FIXED(intensity,particleDescPtr->GreenScale[CurrentVisionMode]), MUL_FIXED(intensity,particleDescPtr->BlueScale[CurrentVisionMode]), particleDescPtr->Alpha ); } } else { colour = particlePtr->Colour; } if (RAINBOWBLOOD_CHEATMODE) { colour = RGBALIGHT_MAKE ( FastRandom()&255, FastRandom()&255, FastRandom()&255, particleDescPtr->Alpha ); } { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } vertexPtr->tu = ((float)(vertices->U>>16)+.5) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)+.5) * RecipH; vertexPtr->rhw = oneOverZ; if (particleDescPtr->IsDrawnInFront) { zvalue = 0.0f; } else if (particleDescPtr->IsDrawnAtBack) { zvalue = 1.0f; } else { zvalue = 1.0f - ZNear*oneOverZ; } vertexPtr->color = colour; vertexPtr->sz = zvalue; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,255);//RGBALIGHT_MAKE(vertices->SpecularR,vertices->SpecularG,vertices->SpecularB,fog); NumVertices++; vertices++; } while(--i); } // set correct texture handle if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(particleDescPtr->TranslucencyType); if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } D3D_OutputTriangles(); } #endif } void D3D_FMVParticle_Output(RENDERVERTEX *renderVerticesPtr) { D3DTEXTUREHANDLE TextureHandle = FMVTextureHandle[0]; float RecipW, RecipH; RecipW = 1.0 /128.0; RecipH = 1.0 /128.0; int colour = FMVParticleColour&0xffffff; { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } vertexPtr->tu = ((float)(vertices->U>>16)) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)) * RecipH; vertexPtr->rhw = oneOverZ; zvalue = 1.0 - ZNear*oneOverZ; // vertexPtr->color = colour; vertexPtr->color = (colour)+(vertices->A<<24); vertexPtr->sz = zvalue; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,255);//RGBALIGHT_MAKE(vertices->SpecularR,vertices->SpecularG,vertices->SpecularB,fog); NumVertices++; vertices++; } while(--i); } // set correct texture handle if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } D3D_OutputTriangles(); } } extern int CloakingPhase; extern int NumActiveBlocks; extern DISPLAYBLOCK *ActiveBlockList[]; extern int GlobalAmbience; extern unsigned char *ScreenBuffer; extern long BackBufferPitch; unsigned short FlameFunction(int x, int y); void InitRandomArrays(void); int Turbulence(int x, int y, int t); void UpdateForceField(void); void D3D_DrawForceField(int xOrigin, int yOrigin, int zOrigin, int fieldType); void UpdateWaterFall(void); void D3D_DrawWaterFall(int xOrigin, int yOrigin, int zOrigin); void D3D_DrawPowerFence(int xOrigin, int yOrigin, int zOrigin, int xScale, int yScale, int zScale); void D3D_DrawExplosion(int xOrigin, int yOrigin, int zOrigin, int size); void D3D_DrawWaterPatch(int xOrigin, int yOrigin, int zOrigin); void D3D_DrawWaterOctagonPatch(int xOrigin, int yOrigin, int zOrigin, int xOffset, int zOffset); int LightSourceWaterPoint(VECTORCH *pointPtr,int offset); void D3D_DrawWaterMesh_Unclipped(void); void D3D_DrawWaterMesh_Clipped(void); void D3D_DrawMoltenMetal(int xOrigin, int yOrigin, int zOrigin); void D3D_DrawMoltenMetalMesh_Unclipped(void); void D3D_DrawMoltenMetalMesh_Clipped(void); //#define WATER_POLY_SCALE 256 int MeshXScale; int MeshZScale; int WaterFallBase; void PostLandscapeRendering(void) { extern int NumOnScreenBlocks; extern DISPLAYBLOCK *OnScreenBlockList[]; int numOfObjects = NumOnScreenBlocks; extern char LevelName[]; CurrentRenderStates.FogIsOn = 1; if (!strcmp(LevelName,"fall")||!strcmp(LevelName,"fall_m")) { char drawWaterFall = 0; char drawStream = 0; while(numOfObjects) { DISPLAYBLOCK *objectPtr = OnScreenBlockList[--numOfObjects]; MODULE *modulePtr = objectPtr->ObMyModule; /* if it's a module, which isn't inside another module */ if (modulePtr && modulePtr->name) { if( (!strcmp(modulePtr->name,"fall01")) ||(!strcmp(modulePtr->name,"well01")) ||(!strcmp(modulePtr->name,"well02")) ||(!strcmp(modulePtr->name,"well03")) ||(!strcmp(modulePtr->name,"well04")) ||(!strcmp(modulePtr->name,"well05")) ||(!strcmp(modulePtr->name,"well06")) ||(!strcmp(modulePtr->name,"well07")) ||(!strcmp(modulePtr->name,"well08")) ||(!strcmp(modulePtr->name,"well"))) { drawWaterFall = 1; } else if( (!strcmp(modulePtr->name,"stream02")) ||(!strcmp(modulePtr->name,"stream03")) ||(!strcmp(modulePtr->name,"watergate"))) { drawStream = 1; } } } if (drawWaterFall) { // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } OP_STATE_RENDER(1, ExecBufInstPtr); //STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_ALWAYS, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); //UpdateWaterFall(); WaterFallBase = 109952; MeshZScale = (66572-51026)/15; MeshXScale = (109952+3039)/45; D3D_DrawWaterFall(175545,-3039,51026); // MeshZScale = -(538490-392169); // MeshXScale = 55000; // D3D_DrawWaterPatch(-100000, WaterFallBase, 538490); OP_STATE_RENDER(1, ExecBufInstPtr); //STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); } if (drawStream) { int x = 68581; int y = 12925; int z = 93696; MeshXScale = (87869-68581); MeshZScale = (105385-93696); { extern void CheckForObjectsInWater(int minX, int maxX, int minZ, int maxZ, int averageY); CheckForObjectsInWater(x, x+MeshXScale, z, z+MeshZScale, y); } WaterXOrigin=x; WaterZOrigin=z; WaterUScale = 4.0f/(float)MeshXScale; WaterVScale = 4.0f/(float)MeshZScale; MeshXScale/=4; MeshZScale/=2; // Turn OFF texturing if it is on... D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[ChromeImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } D3D_DrawWaterPatch(x, y, z); D3D_DrawWaterPatch(x+MeshXScale, y, z); D3D_DrawWaterPatch(x+MeshXScale*2, y, z); D3D_DrawWaterPatch(x+MeshXScale*3, y, z); D3D_DrawWaterPatch(x, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*2, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*3, y, z+MeshZScale); } } #if 0 else if ( (!__stricmp(LevelName,"e3demo")) || (!__stricmp(LevelName,"e3demosp")) ) { int drawOctagonPool = -1; int drawFMV = -1; int drawPredatorFMV = -1; int drawSwirlyFMV = -1; int drawSwirlyFMV2 = -1; int drawSwirlyFMV3 = -1; while(numOfObjects) { DISPLAYBLOCK *objectPtr = OnScreenBlockList[--numOfObjects]; MODULE *modulePtr = objectPtr->ObMyModule; /* if it's a module, which isn't inside another module */ if (modulePtr && modulePtr->name) { if(!__stricmp(modulePtr->name,"water1")) { drawOctagonPool = modulePtr->m_index; } else if(!__stricmp(modulePtr->name,"marine01b")) { drawFMV = modulePtr->m_index; } else if(!_stricmp(modulePtr->name,"predator01")) { drawPredatorFMV = modulePtr->m_index; } else if(!_stricmp(modulePtr->name,"toptopgr01")) { drawSwirlyFMV = modulePtr->m_index; } else if(!_stricmp(modulePtr->name,"grille04")) { drawSwirlyFMV2 = modulePtr->m_index; } #if 0 else if(!_stricmp(modulePtr->name,"marine05")) { drawSwirlyFMV3 = modulePtr->m_index; } #endif } } #if FMV_ON // UpdateFMVTextures(3); if (drawFMV!=-1) { DECAL fmvDecal = { DECAL_FMV, }; fmvDecal.ModuleIndex = drawFMV; fmvDecal.UOffset = 0; UpdateFMVTextures(4); for (int z=0; z<6; z++) { for (int y=0; y<3; y++) { fmvDecal.Vertices[0].vx = -149; fmvDecal.Vertices[1].vx = -149; fmvDecal.Vertices[2].vx = -149; fmvDecal.Vertices[3].vx = -149; fmvDecal.Vertices[0].vy = -3254+y*744; fmvDecal.Vertices[1].vy = -3254+y*744; fmvDecal.Vertices[2].vy = -3254+y*744+744; fmvDecal.Vertices[3].vy = -3254+y*744+744; fmvDecal.Vertices[0].vz = 49440+z*993; fmvDecal.Vertices[1].vz = 49440+z*993+993; fmvDecal.Vertices[2].vz = 49440+z*993+993; fmvDecal.Vertices[3].vz = 49440+z*993; fmvDecal.Centre.vx = ((z+y)%3)+1; RenderDecal(&fmvDecal); } } } if (drawPredatorFMV!=-1) { DECAL fmvDecal = { DECAL_FMV, }; fmvDecal.ModuleIndex = drawPredatorFMV; fmvDecal.UOffset = 0; UpdateFMVTextures(4); for (int z=0; z<12; z++) { for (int y=0; y<7; y++) { fmvDecal.Vertices[0].vx = -7164; fmvDecal.Vertices[1].vx = -7164; fmvDecal.Vertices[2].vx = -7164; fmvDecal.Vertices[3].vx = -7164; fmvDecal.Vertices[0].vy = -20360+y*362; fmvDecal.Vertices[1].vy = -20360+y*362; fmvDecal.Vertices[2].vy = -20360+y*362+362; fmvDecal.Vertices[3].vy = -20360+y*362+362; fmvDecal.Vertices[0].vz = 1271+z*483+483; fmvDecal.Vertices[1].vz = 1271+z*483; fmvDecal.Vertices[2].vz = 1271+z*483; fmvDecal.Vertices[3].vz = 1271+z*483+483; fmvDecal.Centre.vx = (z+y)%3; RenderDecal(&fmvDecal); } } } #endif if (drawSwirlyFMV!=-1) { UpdateFMVTextures(1); D3D_DrawSwirlyFMV(30000,-12500,0); } if (drawSwirlyFMV2!=-1) { UpdateFMVTextures(1); D3D_DrawSwirlyFMV(2605,-6267-2000,17394-3200); } if (drawSwirlyFMV3!=-1) { // UpdateFMVTextures(1); D3D_DrawSwirlyFMV(5117,3456-3000,52710-2000); } if (drawOctagonPool!=-1) { #if FMV_ON UpdateFMVTextures(1); MeshXScale = (3000); MeshZScale = (4000); D3D_DrawFMVOnWater(-1000,3400,22000); { DECAL fmvDecal = { DECAL_FMV, { {0,-2500,29000}, {2000,-2500,29000}, {2000,-2500+750*2,29000}, {0,-2500+750*2,29000} }, 0 }; fmvDecal.ModuleIndex = drawOctagonPool; fmvDecal.Centre.vx = 0; fmvDecal.UOffset = 0; RenderDecal(&fmvDecal); } #endif int highDetailRequired = 1; int x = 1023; int y = 3400; int z = 27536; { int dx = Player->ObWorld.vx - x; if (dx< -8000 || dx > 8000) { highDetailRequired = 0; } else { int dz = Player->ObWorld.vz - z; if (dz< -8000 || dz > 8000) { highDetailRequired = 0; } } } MeshXScale = 7700; MeshZScale = 7700; { extern void CheckForObjectsInWater(int minX, int maxX, int minZ, int maxZ, int averageY); CheckForObjectsInWater(x-MeshXScale, x+MeshXScale, z-MeshZScale, z+MeshZScale, y); } MeshXScale /=15; MeshZScale /=15; // Turn OFF texturing if it is on... D3DTEXTUREHANDLE TextureHandle = NULL; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } if (highDetailRequired) { MeshXScale /= 2; MeshZScale /= 2; D3D_DrawWaterOctagonPatch(x,y,z,0,0); D3D_DrawWaterOctagonPatch(x,y,z,15,0); D3D_DrawWaterOctagonPatch(x,y,z,0,15); D3D_DrawWaterOctagonPatch(x,y,z,15,15); MeshXScale = -MeshXScale; D3D_DrawWaterOctagonPatch(x,y,z,0,0); D3D_DrawWaterOctagonPatch(x,y,z,15,0); D3D_DrawWaterOctagonPatch(x,y,z,0,15); D3D_DrawWaterOctagonPatch(x,y,z,15,15); MeshZScale = -MeshZScale; D3D_DrawWaterOctagonPatch(x,y,z,0,0); D3D_DrawWaterOctagonPatch(x,y,z,15,0); D3D_DrawWaterOctagonPatch(x,y,z,0,15); D3D_DrawWaterOctagonPatch(x,y,z,15,15); MeshXScale = -MeshXScale; D3D_DrawWaterOctagonPatch(x,y,z,0,0); D3D_DrawWaterOctagonPatch(x,y,z,15,0); D3D_DrawWaterOctagonPatch(x,y,z,0,15); D3D_DrawWaterOctagonPatch(x,y,z,15,15); } else { D3D_DrawWaterOctagonPatch(x,y,z,0,0); MeshXScale = -MeshXScale; D3D_DrawWaterOctagonPatch(x,y,z,0,0); MeshZScale = -MeshZScale; D3D_DrawWaterOctagonPatch(x,y,z,0,0); MeshXScale = -MeshXScale; D3D_DrawWaterOctagonPatch(x,y,z,0,0); } } } #endif else if (!_stricmp(LevelName,"hangar")) { #if FMV_ON #if WIBBLY_FMV_ON UpdateFMVTextures(1); D3D_DrawFMV(FmvPosition.vx,FmvPosition.vy,FmvPosition.vz); #endif #endif #if 0 { VECTORCH v = {49937,-4000,-37709}; // hangar D3D_DrawCable(&v); } #endif } else if (!_stricmp(LevelName,"invasion_a")) { char drawWater = 0; char drawEndWater = 0; while(numOfObjects) { DISPLAYBLOCK *objectPtr = OnScreenBlockList[--numOfObjects]; MODULE *modulePtr = objectPtr->ObMyModule; /* if it's a module, which isn't inside another module */ if (modulePtr && modulePtr->name) { if( (!strcmp(modulePtr->name,"hivepool")) ||(!strcmp(modulePtr->name,"hivepool04"))) { drawWater = 1; break; } else { if(!strcmp(modulePtr->name,"shaftbot")) { drawEndWater = 1; } if((!_stricmp(modulePtr->name,"shaft01")) ||(!_stricmp(modulePtr->name,"shaft02")) ||(!_stricmp(modulePtr->name,"shaft03")) ||(!_stricmp(modulePtr->name,"shaft04")) ||(!_stricmp(modulePtr->name,"shaft05")) ||(!_stricmp(modulePtr->name,"shaft06"))) { extern void HandleRainShaft(MODULE *modulePtr, int bottomY, int topY, int numberOfRaindrops); HandleRainShaft(modulePtr, -11726,-107080,10); drawEndWater = 1; break; } } } } if (drawWater) { int x = 20767; int y = -36000+200; int z = 30238; MeshXScale = (36353-20767); MeshZScale = (41927-30238); { extern void CheckForObjectsInWater(int minX, int maxX, int minZ, int maxZ, int averageY); CheckForObjectsInWater(x, x+MeshXScale, z, z+MeshZScale, y); } WaterXOrigin=x; WaterZOrigin=z; WaterUScale = 4.0f/(float)MeshXScale; WaterVScale = 4.0f/(float)MeshZScale; MeshXScale/=4; MeshZScale/=2; // Turn OFF texturing if it is on... D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[ChromeImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } D3D_DrawWaterPatch(x, y, z); D3D_DrawWaterPatch(x+MeshXScale, y, z); D3D_DrawWaterPatch(x+MeshXScale*2, y, z); D3D_DrawWaterPatch(x+MeshXScale*3, y, z); D3D_DrawWaterPatch(x, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*2, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*3, y, z+MeshZScale); } else if (drawEndWater) { int x = -15471; int y = -11720-500; int z = -55875; MeshXScale = (15471-1800); MeshZScale = (55875-36392); { extern void CheckForObjectsInWater(int minX, int maxX, int minZ, int maxZ, int averageY); CheckForObjectsInWater(x, x+MeshXScale, z, z+MeshZScale, y); } WaterXOrigin=x; WaterZOrigin=z; WaterUScale = 4.0f/(float)(MeshXScale+1800-3782); WaterVScale = 4.0f/(float)MeshZScale; MeshXScale/=4; MeshZScale/=2; // Turn OFF texturing if it is on... D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[WaterShaftImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } D3D_DrawWaterPatch(x, y, z); D3D_DrawWaterPatch(x+MeshXScale, y, z); D3D_DrawWaterPatch(x+MeshXScale*2, y, z); D3D_DrawWaterPatch(x+MeshXScale*3, y, z); D3D_DrawWaterPatch(x, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*2, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*3, y, z+MeshZScale); } } #if 1 else if (!_stricmp(LevelName,"derelict")) { char drawMirrorSurfaces = 0; char drawWater = 0; while(numOfObjects) { DISPLAYBLOCK *objectPtr = OnScreenBlockList[--numOfObjects]; MODULE *modulePtr = objectPtr->ObMyModule; /* if it's a module, which isn't inside another module */ if (modulePtr && modulePtr->name) { if( (!_stricmp(modulePtr->name,"start-en01")) ||(!_stricmp(modulePtr->name,"start"))) { drawMirrorSurfaces = 1; } else if (!_stricmp(modulePtr->name,"water-01")) { extern void HandleRainShaft(MODULE *modulePtr, int bottomY, int topY, int numberOfRaindrops); drawWater = 1; HandleRainShaft(modulePtr, 32000, 0, 16); } } } if (drawMirrorSurfaces) { extern void RenderMirrorSurface(void); extern void RenderMirrorSurface2(void); extern void RenderParticlesInMirror(void); RenderParticlesInMirror(); RenderMirrorSurface(); RenderMirrorSurface2(); } if (drawWater) { int x = -102799; int y = 32000; int z = -200964; MeshXScale = (102799-87216); MeshZScale = (200964-180986); { extern void CheckForObjectsInWater(int minX, int maxX, int minZ, int maxZ, int averageY); CheckForObjectsInWater(x, x+MeshXScale, z, z+MeshZScale, y); } WaterXOrigin=x; WaterZOrigin=z; WaterUScale = 4.0f/(float)MeshXScale; WaterVScale = 4.0f/(float)MeshZScale; MeshXScale/=2; MeshZScale/=2; // Turn OFF texturing if it is on... D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[ChromeImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } D3D_DrawWaterPatch(x, y, z); D3D_DrawWaterPatch(x+MeshXScale, y, z); D3D_DrawWaterPatch(x, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale); } } #endif else if (!_stricmp(LevelName,"genshd1")) { char drawWater = 0; while(numOfObjects) { DISPLAYBLOCK *objectPtr = OnScreenBlockList[--numOfObjects]; MODULE *modulePtr = objectPtr->ObMyModule; /* if it's a module, which isn't inside another module */ if (modulePtr && modulePtr->name) { if( (!_stricmp(modulePtr->name,"largespace")) ||(!_stricmp(modulePtr->name,"proc13")) ||(!_stricmp(modulePtr->name,"trench01")) ||(!_stricmp(modulePtr->name,"trench02")) ||(!_stricmp(modulePtr->name,"trench03")) ||(!_stricmp(modulePtr->name,"trench04")) ||(!_stricmp(modulePtr->name,"trench05")) ||(!_stricmp(modulePtr->name,"trench06")) ||(!_stricmp(modulePtr->name,"trench07")) ||(!_stricmp(modulePtr->name,"trench08")) ||(!_stricmp(modulePtr->name,"trench09"))) { extern void HandleRain(int numberOfRaindrops); HandleRain(999); break; } } } } } void D3D_DrawWaterTest(MODULE *testModulePtr) { extern char LevelName[]; if (!strcmp(LevelName,"genshd1")) { extern DISPLAYBLOCK *Player; // DISPLAYBLOCK *objectPtr = OnScreenBlockList[numOfObjects]; MODULE *modulePtr = testModulePtr;//objectPtr->ObMyModule; #if 0 if (testModulePtr && testModulePtr->name) if(!strcmp(testModulePtr->name,"LargeSpace")) { extern void HandleRain(int numberOfRaindrops); HandleRain(999); } #endif if (modulePtr && modulePtr->name) { if (!strcmp(modulePtr->name,"05")) { int y = modulePtr->m_maxy+modulePtr->m_world.vy-500; int x = modulePtr->m_minx+modulePtr->m_world.vx; int z = modulePtr->m_minz+modulePtr->m_world.vz; MeshXScale = (7791 - -7794); MeshZScale = (23378 - 7793); { extern void CheckForObjectsInWater(int minX, int maxX, int minZ, int maxZ, int averageY); CheckForObjectsInWater(x, x+MeshXScale, z, z+MeshZScale, y); } D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[WaterShaftImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } WaterXOrigin=x; WaterZOrigin=z; WaterUScale = 4.0f/(float)(MeshXScale); WaterVScale = 4.0f/(float)MeshZScale; #if 1 MeshXScale/=2; MeshZScale/=2; D3D_DrawWaterPatch(x, y, z); D3D_DrawWaterPatch(x+MeshXScale, y, z); D3D_DrawWaterPatch(x, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale); extern void HandleRainShaft(MODULE *modulePtr, int bottomY, int topY, int numberOfRaindrops); HandleRainShaft(modulePtr, y,-21000,1); #else MeshXScale/=4; MeshZScale/=4; D3D_DrawWaterPatch(x, y, z); D3D_DrawWaterPatch(x, y, z+MeshZScale); D3D_DrawWaterPatch(x, y, z+MeshZScale*2); D3D_DrawWaterPatch(x, y, z+MeshZScale*3); D3D_DrawWaterPatch(x+MeshXScale, y, z); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale*2); D3D_DrawWaterPatch(x+MeshXScale, y, z+MeshZScale*3); D3D_DrawWaterPatch(x+MeshXScale*2, y, z); D3D_DrawWaterPatch(x+MeshXScale*2, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*2, y, z+MeshZScale*2); D3D_DrawWaterPatch(x+MeshXScale*2, y, z+MeshZScale*3); D3D_DrawWaterPatch(x+MeshXScale*3, y, z); D3D_DrawWaterPatch(x+MeshXScale*3, y, z+MeshZScale); D3D_DrawWaterPatch(x+MeshXScale*3, y, z+MeshZScale*2); D3D_DrawWaterPatch(x+MeshXScale*3, y, z+MeshZScale*3); HandleRainDrops(modulePtr,2); #endif } } } #if 0 else if ( (!_stricmp(LevelName,"e3demo")) || (!_stricmp(LevelName,"e3demosp")) ) { if (testModulePtr && testModulePtr->name) { #if 0 if(!_stricmp(testModulePtr->name,"watermid")) { DECAL fmvDecal = { DECAL_FMV, { {0,-2500,29000}, {2000,-2500,29000}, {2000,-2500+750*2,29000}, {0,-2500+750*2,29000} }, 0 }; fmvDecal.ModuleIndex = testModulePtr->m_index; fmvDecal.Centre.vx = 0; fmvDecal.UOffset = 0; RenderDecal(&fmvDecal); } #endif if(!_stricmp(testModulePtr->name,"lowlowlo03")) { VECTORCH position = {6894,469,-13203}; VECTORCH disp = position; int i,d; disp.vx -= Player->ObWorld.vx; disp.vy -= Player->ObWorld.vy; disp.vz -= Player->ObWorld.vz; d = ONE_FIXED - Approximate3dMagnitude(&disp)*2; if (d<0) d = 0; i = MUL_FIXED(10,d); while(i--) { VECTORCH velocity; velocity.vx = ((FastRandom()&1023) - 512); velocity.vy = ((FastRandom()&1023) - 512)+2000; velocity.vz = (1000+(FastRandom()&255))*2; MakeParticle(&(position),&(velocity),PARTICLE_STEAM); } } } } #endif } VECTORCH MeshVertex[256]; #define TEXTURE_WATER 0 VECTORCH MeshWorldVertex[256]; unsigned int MeshVertexColour[256]; unsigned int MeshVertexSpecular[256]; char MeshVertexOutcode[256]; void D3D_DrawWaterPatch(int xOrigin, int yOrigin, int zOrigin) { int i=0; int x; for (x=0; x<16; x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; point->vx = xOrigin+(x*MeshXScale)/15; point->vz = zOrigin+(z*MeshZScale)/15; int offset=0; #if 1 /* basic noise ripples */ // offset = MUL_FIXED(32,GetSin( (point->vx+point->vz+CloakingPhase)&4095 ) ); // offset += MUL_FIXED(16,GetSin( (point->vx-point->vz*2+CloakingPhase/2)&4095 ) ); { offset += EffectOfRipples(point); } #endif // if (offset>450) offset = 450; // if (offset<-450) offset = -450; point->vy = yOrigin+offset; #if 0 MeshVertexColour[i] = LightSourceWaterPoint(point,offset); #else { int alpha = 128-offset/4; // if (alpha>255) alpha = 255; // if (alpha<128) alpha = 128; switch (CurrentVisionMode) { default: case VISION_MODE_NORMAL: { // MeshVertexColour[i] = RGBALIGHT_MAKE(10,51,28,alpha); MeshVertexColour[i] = RGBALIGHT_MAKE(255,255,255,alpha); #if 0 #if 1 VECTORCH pos = {24087,yOrigin,39165}; int c = (8191-VectorDistance(&pos,point)); if (c<0) c=0; else { int s = GetSin((CloakingPhase/2)&4095); s = MUL_FIXED(s,s)/64; c = MUL_FIXED(s,c); } MeshVertexSpecular[i] = (c<<16)+(((c/4)<<8)&0xff00) + (c/4); #else if (!(FastRandom()&1023)) { MeshVertexSpecular[i] = 0xc04040; } else { MeshVertexSpecular[i] = 0; } #endif #endif break; } case VISION_MODE_IMAGEINTENSIFIER: { MeshVertexColour[i] = RGBALIGHT_MAKE(0,51,0,alpha); break; } case VISION_MODE_PRED_THERMAL: case VISION_MODE_PRED_SEEALIENS: case VISION_MODE_PRED_SEEPREDTECH: { MeshVertexColour[i] = RGBALIGHT_MAKE(0,0,28,alpha); break; } } } #endif #if 1 MeshWorldVertex[i].vx = ((point->vx-WaterXOrigin)/4+MUL_FIXED(GetSin((point->vy*16)&4095),128)); MeshWorldVertex[i].vy = ((point->vz-WaterZOrigin)/4+MUL_FIXED(GetSin((point->vy*16+200)&4095),128)); #endif #if 1 TranslatePointIntoViewspace(point); #else point->vx -= Global_VDB_Ptr->VDB_World.vx; point->vy -= Global_VDB_Ptr->VDB_World.vy; point->vz -= Global_VDB_Ptr->VDB_World.vz; RotateVector(point,&(Global_VDB_Ptr->VDB_Mat)); point->vy = MUL_FIXED(point->vy,87381); #endif /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawMoltenMetalMesh_Unclipped(); // D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawMoltenMetalMesh_Clipped(); // D3D_DrawWaterMesh_Clipped(); } } void D3D_DrawWaterMesh_Unclipped(void) { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; VECTORCH *point = MeshVertex; #if TEXTURE_WATER VECTORCH *pointWS = MeshWorldVertex; #endif int i; for (i=0; i<256; i++) { if (point->vz<=1) point->vz = 1; int x = (point->vx*(Global_VDB_Ptr->VDB_ProjX))/point->vz+Global_VDB_Ptr->VDB_CentreX; int y = (point->vy*(Global_VDB_Ptr->VDB_ProjY))/point->vz+Global_VDB_Ptr->VDB_CentreY; // textprint("%d, %d\n",x,y); #if 1 { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } #else vertexPtr->sx=x; vertexPtr->sy=y; #endif #if FOG_ON { int fog = (point->vz)/FOG_SCALE; if (fog<0) fog=0; if (fog>254) fog=254; fog=255-fog; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,fog); } #endif point->vz+=HeadUpDisplayZOffset; float oneOverZ = ((float)(point->vz)-ZNear)/(float)(point->vz); //vertexPtr->color = RGBALIGHT_MAKE(66,70,0,127+(FastRandom()&63)); vertexPtr->color = MeshVertexColour[i]; vertexPtr->sz = oneOverZ; #if TEXTURE_WATER vertexPtr->tu = pointWS->vx/128.0; vertexPtr->tv = pointWS->vz/128.0; #endif NumVertices++; vertexPtr++; point++; #if TEXTURE_WATER pointWS++; #endif } } // textprint("numvertices %d\n",NumVertices); /* * Make sure that the triangle data (not OP) will be QWORD aligned */ if (QWORD_ALIGNED(ExecBufInstPtr)) { OP_NOP(ExecBufInstPtr); } OP_TRIANGLE_LIST(450, ExecBufInstPtr); /* CONSTRUCT POLYS */ { int x; for (x=0; x<15; x++) { int y; for(y=0; y<15; y++) { OUTPUT_TRIANGLE(0+x+(16*y),1+x+(16*y),16+x+(16*y), 256); OUTPUT_TRIANGLE(1+x+(16*y),17+x+(16*y),16+x+(16*y), 256); } } } #if 1 { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } #endif } void D3D_DrawWaterMesh_Clipped(void) { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; VECTORCH *point = MeshVertex; #if TEXTURE_WATER VECTORCH *pointWS = MeshWorldVertex; #endif int i; for (i=0; i<256; i++) { { if (point->vz<=1) point->vz = 1; int x = (point->vx*(Global_VDB_Ptr->VDB_ProjX))/point->vz+Global_VDB_Ptr->VDB_CentreX; int y = (point->vy*(Global_VDB_Ptr->VDB_ProjY))/point->vz+Global_VDB_Ptr->VDB_CentreY; #if 1 { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } #else vertexPtr->sx=x; vertexPtr->sy=y; #endif #if FOG_ON { int fog = ((point->vz)/FOG_SCALE); if (fog<0) fog=0; if (fog>254) fog=254; fog=255-fog; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,fog); } #endif #if TEXTURE_WATER vertexPtr->tu = pointWS->vx/128.0; vertexPtr->tv = pointWS->vz/128.0; #endif point->vz+=HeadUpDisplayZOffset; float oneOverZ = ((float)(point->vz)-ZNear)/(float)(point->vz); // vertexPtr->color = RGBALIGHT_MAKE(66,70,0,127+(FastRandom()&63)); vertexPtr->color = MeshVertexColour[i]; vertexPtr->sz = oneOverZ; } NumVertices++; vertexPtr++; point++; #if TEXTURE_WATER pointWS++; #endif } } // textprint("numvertices %d\n",NumVertices); /* CONSTRUCT POLYS */ { int x; for (x=0; x<15; x++) { int y; for(y=0; y<15; y++) { #if 1 int p1 = 0+x+(16*y); int p2 = 1+x+(16*y); int p3 = 16+x+(16*y); int p4 = 17+x+(16*y); if (MeshVertexOutcode[p1]||MeshVertexOutcode[p2]||MeshVertexOutcode[p3]) { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(p1,p2,p3, 256); } if (MeshVertexOutcode[p2]||MeshVertexOutcode[p3]||MeshVertexOutcode[p4]) { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(p2,p4,p3, 256); } #else int p2 = 1+x+(16*y); int p3 = 16+x+(16*y); if (MeshVertexOutcode[p2]&&MeshVertexOutcode[p3]) { int p1 = 0+x+(16*y); int p4 = 17+x+(16*y); if (MeshVertexOutcode[p1]) { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(p1,p2,p3, 256); } if (MeshVertexOutcode[p4]) { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(p2,p4,p3, 256); } } #endif } } } #if 1 { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } #endif } int LightSourceWaterPoint(VECTORCH *pointPtr,int offset) { // this needs a rewrite... // make a list of lights which will affect some part of the mesh // and go throught that for each point. // int intensity=0; int redI=0,greenI=0,blueI=0; #if 0 int alpha = 207-offset; if (alpha>255) alpha = 255; if (alpha<160) alpha = 160; return RGBALIGHT_MAKE(128,128,255,alpha); #else DISPLAYBLOCK **activeBlockListPtr = ActiveBlockList; for(int i = NumActiveBlocks; i!=0; i--) { DISPLAYBLOCK *dispPtr = *activeBlockListPtr++; if(dispPtr->ObNumLights) { for(int j = 0; j < dispPtr->ObNumLights; j++) { LIGHTBLOCK *lptr = dispPtr->ObLights[j]; VECTORCH disp = lptr->LightWorld; disp.vx -= pointPtr->vx; disp.vy -= pointPtr->vy; disp.vz -= pointPtr->vz; int dist = Approximate3dMagnitude(&disp); if (distLightRange) { int brightness = MUL_FIXED(lptr->BrightnessOverRange,lptr->LightRange-dist); redI += MUL_FIXED(brightness,lptr->RedScale); greenI += MUL_FIXED(brightness,lptr->GreenScale); blueI += MUL_FIXED(brightness,lptr->BlueScale); } } } } if (redI>ONE_FIXED) redI=ONE_FIXED; else if (redIONE_FIXED) greenI=ONE_FIXED; else if (greenIONE_FIXED) blueI=ONE_FIXED; else if (blueI255) alpha = 255; if (alpha<128) alpha = 128; // return RGBALIGHT_MAKE(MUL_FIXED(64+(offset&128),redI),MUL_FIXED(64+(offset&128),greenI),MUL_FIXED(64+(offset&128),blueI),alpha); // return RGBALIGHT_MAKE(MUL_FIXED(50,redI),MUL_FIXED(255,greenI),MUL_FIXED(140,blueI),alpha); return RGBALIGHT_MAKE(MUL_FIXED(10,redI),MUL_FIXED(51,greenI),MUL_FIXED(28,blueI),alpha); // return RGBALIGHT_MAKE(MUL_FIXED(128,redI),MUL_FIXED(128,greenI),MUL_FIXED(255,blueI),alpha); #endif } int LightIntensityAtPoint(VECTORCH *pointPtr) { int intensity=0; DISPLAYBLOCK **activeBlockListPtr = ActiveBlockList; for(int i = NumActiveBlocks; i!=0; i--) { DISPLAYBLOCK *dispPtr = *activeBlockListPtr++; if(dispPtr->ObNumLights) { for(int j = 0; j < dispPtr->ObNumLights; j++) { LIGHTBLOCK *lptr = dispPtr->ObLights[j]; VECTORCH disp = lptr->LightWorld; disp.vx -= pointPtr->vx; disp.vy -= pointPtr->vy; disp.vz -= pointPtr->vz; int dist = Approximate3dMagnitude(&disp); if (distLightRange) { intensity += WideMulNarrowDiv(lptr->LightBright,lptr->LightRange-dist,lptr->LightRange); } } } } if (intensity>ONE_FIXED) intensity=ONE_FIXED; else if (intensity>6; ForceFieldPhase+=NormalFrameTime>>5; int x; for (x=1; x<15*3; x++) { int y; for (y=1; y<15; y++) { int acceleration =32*(-8*ForceFieldPointDisplacement[x][y] +ForceFieldPointDisplacement[x-1][y-1] +ForceFieldPointDisplacement[x-1][y] +ForceFieldPointDisplacement[x-1][y+1] +ForceFieldPointDisplacement[x][y-1] +ForceFieldPointDisplacement[x][y+1] #if 0 ) #else +ForceFieldPointDisplacement[x+1][y-1] +ForceFieldPointDisplacement[x+1][y] +ForceFieldPointDisplacement[x+1][y+1]) #endif -(ForceFieldPointVelocity[x][y]*5); ForceFieldPointVelocity[x][y] += MUL_FIXED(acceleration,NormalFrameTime); ForceFieldPointDisplacement2[x][y] += MUL_FIXED(ForceFieldPointVelocity[x][y],NormalFrameTime); #if 1 if(ForceFieldPointDisplacement2[x][y]>200) ForceFieldPointDisplacement2[x][y]=200; if(ForceFieldPointDisplacement2[x][y]<-200) ForceFieldPointDisplacement2[x][y]=-200; #else if(ForceFieldPointDisplacement2[x][y]>512) ForceFieldPointDisplacement2[x][y]=512; if(ForceFieldPointDisplacement2[x][y]<-512) ForceFieldPointDisplacement2[x][y]=-512; #endif { int offset = ForceFieldPointDisplacement2[x][y]; int colour = ForceFieldPointVelocity[x][y]/4; if (offset<0) offset =-offset; if (colour<0) colour =-colour; colour=(colour+offset)/2; if(colour>255) colour=255; colour++; ForceFieldPointColour1[x][y]=FastRandom()%colour; ForceFieldPointColour2[x][y]=FastRandom()%colour; } } } for (x=1; x<15*3; x++) { int y; for (y=1; y<15; y++) { ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement2[x][y]; } } { #if 1 if(ForceFieldPhase>1000) { ForceFieldPhase=0; int x = 1+(FastRandom()%(15*3-2)); int y = 1+(FastRandom()%13); ForceFieldPointVelocity[x][y] = 10000; ForceFieldPointVelocity[x][y+1] = 10000; ForceFieldPointVelocity[x+1][y] = 10000; ForceFieldPointVelocity[x+1][y+1] = 10000; } #else // if(ForceFieldPhase>1000) { ForceFieldPhase=0; int x = 1+(FastRandom()%(15*3-2)); int y = 1+(FastRandom()%13); ForceFieldPointVelocity[x][y] = (FastRandom()&16383)+8192; } #endif } #else int x; int y; for (y=0; y<=15; y++) { ForceFieldPointDisplacement[0][y] += (FastRandom()&127)-64; if(ForceFieldPointDisplacement[0][y]>512) ForceFieldPointDisplacement[0][y]=512; if(ForceFieldPointDisplacement[0][y]<-512) ForceFieldPointDisplacement[0][y]=-512; ForceFieldPointVelocity[0][y] = (FastRandom()&16383)-8192; } for (x=15*3-1; x>0; x--) { for (y=0; y<=15; y++) { ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement[x-1][y]; ForceFieldPointVelocity[x][y] = ForceFieldPointVelocity[x-1][y]; } } for (x=15*3-1; x>1; x--) { y = FastRandom()&15; ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement[x-1][y]; y = (FastRandom()&15)-1; ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement[x-1][y]; } #endif } void UpdateWaterFall(void) { int x; int y; for (y=0; y<=15; y++) { ForceFieldPointDisplacement[0][y] += (FastRandom()&127)-64; if(ForceFieldPointDisplacement[0][y]>512) ForceFieldPointDisplacement[0][y]=512; if(ForceFieldPointDisplacement[0][y]<-512) ForceFieldPointDisplacement[0][y]=-512; ForceFieldPointVelocity[0][y] = (FastRandom()&16383)-8192; } for (x=15*3-1; x>0; x--) { for (y=0; y<=15; y++) { ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement[x-1][y]; ForceFieldPointVelocity[x][y] = ForceFieldPointVelocity[x-1][y]; } } for (x=15*3-1; x>1; x--) { y = FastRandom()&15; ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement[x-1][y]; y = (FastRandom()&15)-1; ForceFieldPointDisplacement[x][y] = ForceFieldPointDisplacement[x-1][y]; } } #endif void D3D_DrawForceField(int xOrigin, int yOrigin, int zOrigin, int fieldType) { MeshXScale = 4096/16; MeshZScale = 4096/16; for (int field=0; field<3; field++) { int i=0; int x; for (x=(0+field*15); x<(16+field*15); x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; int offset = ForceFieldPointDisplacement[x][z]; switch(fieldType) { case 0: { point->vx = xOrigin+(x*MeshXScale); point->vy = yOrigin+(z*MeshZScale); point->vz = zOrigin+offset; break; } case 1: { int theta = (z*4095)/15; int u = (x*65536)/45; int b = MUL_FIXED(2*u,(65536-u)); int c = MUL_FIXED(u,u); int phi = (Phase&4095); int x3 = (GetSin(phi))/64; int y3 = 5000-(GetCos((phi*3+1000)&4095)/128); int z3 = (GetSin((3*phi+1324)&4095))/32; int x2 = -x3/2; int y2 = 3000; int z2 = -z3/4; int innerRadius = 100;//GetSin(u/32)/16+offset; point->vx = xOrigin+(b*x2+c*x3)/65536+MUL_FIXED(innerRadius,GetSin(theta)); point->vy = yOrigin-5000+(b*y2+c*y3)/65536; point->vz = zOrigin+(b*z2+c*z3)/65536+MUL_FIXED(innerRadius,GetCos(theta)); break; } case 2: { int theta = (z*4095)/15; int phi = (x*4095)/45; int innerRadius = 1000+offset; int outerRadius = 4000; point->vx = xOrigin+MUL_FIXED(outerRadius-MUL_FIXED(innerRadius,GetSin(theta)),GetCos(phi)); point->vy = yOrigin+MUL_FIXED(innerRadius,GetCos(theta)); point->vz = zOrigin+MUL_FIXED(outerRadius-MUL_FIXED(innerRadius,GetSin(theta)),GetSin(phi)); break; } case 3: { int theta = (x*4095)/45; int radius = offset+2000; point->vx = xOrigin+MUL_FIXED(radius,GetCos(theta)); point->vy = yOrigin+(z*MeshZScale); point->vz = zOrigin+MUL_FIXED(radius,GetSin(theta)); break; } } if (offset<0) offset =-offset; offset+=16; // offset-=32; // if (offset<0) offset = 0; if(offset>255) offset=255; MeshVertexColour[i] = RGBALIGHT_MAKE(ForceFieldPointColour1[x][z],ForceFieldPointColour2[x][z],255,offset); #if TEXTURE_WATER MeshWorldVertex[i].vx = point->vx; MeshWorldVertex[i].vz = point->vz; #endif TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } //textprint("\n"); if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawWaterMesh_Clipped(); } } } void D3D_DrawPowerFence(int xOrigin, int yOrigin, int zOrigin, int xScale, int yScale, int zScale) { for (int field=0; field<3; field++) { int i=0; int x; for (x=(0+field*15); x<(16+field*15); x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; int offset = ForceFieldPointDisplacement[x][z]; point->vx = xOrigin+(x*xScale); point->vy = yOrigin+(z*yScale); point->vz = zOrigin+(x*zScale); if (offset<0) offset =-offset; offset+=16; if(offset>255) offset=255; MeshVertexColour[i] = RGBALIGHT_MAKE(ForceFieldPointColour1[x][z],ForceFieldPointColour2[x][z],255,offset); /* translate particle into view space */ TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } //textprint("\n"); if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawWaterMesh_Clipped(); } } } void D3D_DrawWaterFall(int xOrigin, int yOrigin, int zOrigin) { { int noRequired = MUL_FIXED(250,NormalFrameTime); for (int i=0; ivx = xOrigin+MUL_FIXED(b,x2)+MUL_FIXED(c,x3)+offset; point->vy = yOrigin+MUL_FIXED(b,y2)+MUL_FIXED(c,y3); point->vz = zOrigin+(z*MeshZScale); if (point->vy>4742) { if (z<=4) { point->vy-=MeshXScale; if (point->vy<4742) point->vy=4742; if (point->vx<179427) point->vx=179427; } else if (z<=8) { point->vx+=(8-z)*1000; } } #else if (offset<0) offset =-offset; point->vx = xOrigin-offset; point->vy = yOrigin+(x*MeshXScale); point->vz = zOrigin+(z*MeshZScale); #endif offset= (offset/4)+127; // offset-=32; // if (offset<0) offset = 0; if(offset>255) offset=255; MeshVertexColour[i] = RGBALIGHT_MAKE(offset,offset,255,offset/2); #if TEXTURE_WATER MeshWorldVertex[i].vx = point->vx; MeshWorldVertex[i].vz = point->vz; #endif /* translate particle into view space */ TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } //textprint("\n"); if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawWaterMesh_Clipped(); } } } void D3D_DrawParticleBeam(DISPLAYBLOCK *muzzlePtr, VECTORCH *targetPositionPtr) { VECTORCH vertices[6]; int beamRadius = 45+(FastRandom()&15); vertices[0] = *targetPositionPtr; vertices[1] = *targetPositionPtr; vertices[2] = *targetPositionPtr; vertices[3] = muzzlePtr->ObWorld; vertices[4] = muzzlePtr->ObWorld; vertices[5] = muzzlePtr->ObWorld; vertices[1].vy += beamRadius; vertices[2].vy -= beamRadius; vertices[4].vy += beamRadius; vertices[5].vy -= beamRadius; /* translate vertices into vxew space */ TranslatePointIntoViewspace(&vertices[0]); TranslatePointIntoViewspace(&vertices[1]); TranslatePointIntoViewspace(&vertices[2]); TranslatePointIntoViewspace(&vertices[3]); TranslatePointIntoViewspace(&vertices[4]); TranslatePointIntoViewspace(&vertices[5]); float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = 6; VECTORCH *verticesPtr = vertices; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; int x = (verticesPtr->vx*(Global_VDB_Ptr->VDB_ProjX))/verticesPtr->vz+Global_VDB_Ptr->VDB_CentreX; int y = (verticesPtr->vy*(Global_VDB_Ptr->VDB_ProjY))/verticesPtr->vz+Global_VDB_Ptr->VDB_CentreY; { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } float oneOverZ = ((float)verticesPtr->vz-ZNear)/(float)verticesPtr->vz; // Different behavxour for different driver modes switch (D3DDriverMode) { default: case D3DSoftwareRGBDriver: case D3DSoftwareRampDriver: break; case D3DHardwareRGBDriver: { if (i==6 || i==3) vertexPtr->color = RGBALIGHT_MAKE(255,255,255,255); else vertexPtr->color = RGBALIGHT_MAKE(0,0,255,32); break; } } vertexPtr->sz = oneOverZ; NumVertices++; verticesPtr++; } while(--i); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); OP_TRIANGLE_LIST(4, ExecBufInstPtr); OUTPUT_TRIANGLE(0,3,5, 6); OUTPUT_TRIANGLE(0,3,4, 6); OUTPUT_TRIANGLE(0,2,5, 6); OUTPUT_TRIANGLE(0,1,4, 6); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } void D3D_DrawExplosion(int xOrigin, int yOrigin, int zOrigin, int size) { if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); MeshXScale = 4096/16; MeshZScale = 4096/16; int i=0; int x; for (x=0; x<16; x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; int offset;// = MUL_FIXED((FastRandom()&1023)-512,CloakingPhase&65535);//MUL_FIXED(255,GetSin((point->vx+point->vy+point->vz+CloakingPhase)&4095)); int sd; { int theta = ((z*2048)/15)&4095; int phi = ((x*4096)/15)&4095; if (theta==0) sd = 0; else sd = phi+theta; if (phi==0 || phi==2048) sd = 0; else sd = phi+theta; int outerRadius = MUL_FIXED(4000,size); if (sd) offset = MUL_FIXED((FastRandom()&511)-255,size); offset=0; point->vx = xOrigin+MUL_FIXED(outerRadius+offset,MUL_FIXED(GetSin(theta),GetCos(phi))); point->vy = yOrigin+MUL_FIXED(outerRadius+offset,MUL_FIXED(GetSin(theta),GetSin(phi))); point->vz = zOrigin+MUL_FIXED(outerRadius+offset,GetCos(theta)); } if(offset<0) offset = -offset; MeshVertexColour[i] = RGBALIGHT_MAKE(255,GetSin((sd+CloakingPhase)&4095)&255,0,32); TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } textprint("drawing explosion\n"); if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawWaterMesh_Clipped(); } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); } void DrawFrameRateBar(void) { extern int NormalFrameTime; #if 1 { int width = DIV_FIXED(ScreenDescriptorBlock.SDB_Width/120,NormalFrameTime); if (width>ScreenDescriptorBlock.SDB_Width) width=ScreenDescriptorBlock.SDB_Width; r2rect rectangle ( 0,0, width, 24 ); textprint("width %d\n",width); rectangle . AlphaFill ( 0xff, // unsigned char R, 0x00,// unsigned char G, 0x00,// unsigned char B, 128 // unsigned char translucency ); } #endif } void D3D_DrawAlienRedBlipIndicatingJawAttack(void) { r2rect rectangle ( 16,16, 32, 32 ); rectangle . AlphaFill ( 0xff, // unsigned char R, 0x00,// unsigned char G, 0x00,// unsigned char B, 128 // unsigned char translucency ); } void D3D_DrawBackdrop(void) { extern char LevelName[]; if (TRIPTASTIC_CHEATMODE||MOTIONBLUR_CHEATMODE) return; if(WireFrameMode) { ColourFillBackBuffer(0); return; } else if(ShowDebuggingText.Tears) { ColourFillBackBuffer((63<<5)); return; } { int needToDrawBackdrop=0; extern int NumActiveBlocks; extern DISPLAYBLOCK *ActiveBlockList[]; int numOfObjects = NumActiveBlocks; while(numOfObjects--) { DISPLAYBLOCK *objectPtr = ActiveBlockList[numOfObjects]; MODULE *modulePtr = objectPtr->ObMyModule; if (modulePtr && (ModuleCurrVisArray[modulePtr->m_index] == 2) &&modulePtr->m_flags&MODULEFLAG_SKY) { needToDrawBackdrop=1; break; } } if(needToDrawBackdrop) { extern BOOL LevelHasStars; extern void RenderSky(void); ColourFillBackBuffer(0); if (LevelHasStars) { extern void RenderStarfield(void); RenderStarfield(); } else { RenderSky(); } return; } } /* if the player is outside the environment, clear the screen! */ { extern MODULE *playerPherModule; if (!playerPherModule) { ColourFillBackBuffer(0); return; } } { PLAYER_STATUS *playerStatusPtr= (PLAYER_STATUS *) (Player->ObStrategyBlock->SBdataptr); if (!playerStatusPtr->IsAlive || FREEFALL_CHEATMODE) { // minimise effects of camera glitches ColourFillBackBuffer(0); return; } } } void MakeNoiseTexture(void) { // return; DDSURFACEDESC ddsd; LPDIRECTDRAWSURFACE tempSurface; LPDIRECT3DTEXTURE tempTexture; LPDIRECTDRAWSURFACE destSurface; LPDIRECT3DTEXTURE destTexture; memcpy(&ddsd, &(d3d.TextureFormat[d3d.CurrentTextureFormat].ddsd), sizeof(ddsd)); ddsd.dwSize = sizeof(ddsd); ddsd.dwFlags = (DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT); ddsd.ddsCaps.dwCaps = (DDSCAPS_SYSTEMMEMORY|DDSCAPS_TEXTURE); ddsd.dwHeight = 256; ddsd.dwWidth = 256; LastError = lpDD->CreateSurface(&ddsd, &tempSurface, NULL); LOGDXERR(LastError); LastError = tempSurface->QueryInterface(IID_IDirect3DTexture, (LPVOID*) &tempTexture); LOGDXERR(LastError); // Query destination surface for a texture interface. memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = tempSurface->GetSurfaceDesc(&ddsd); LOGDXERR(LastError); ddsd.dwFlags = (DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT); ddsd.ddsCaps.dwCaps = (DDSCAPS_TEXTURE | DDSCAPS_ALLOCONLOAD ); LastError = lpDD->CreateSurface(&ddsd, &destSurface, NULL); LOGDXERR(LastError); /* KJL 11:59:21 09/02/98 - check for palettised modes */ { int PalCaps; if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { PalCaps = (DDPCAPS_8BIT | DDPCAPS_ALLOW256); } #if 0 else if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED4) { PalCaps = DDPCAPS_4BIT; } else #endif { PalCaps = 0; } if (PalCaps) { LPDIRECTDRAWPALETTE destPalette = NULL; PALETTEENTRY palette[256]; memset(palette, 0, sizeof(PALETTEENTRY) * 256); for(int i=0;i<256;i++) { palette[i].peRed = i; palette[i].peGreen = i; palette[i].peBlue = i; } LastError = lpDD->CreatePalette(PalCaps, palette, &destPalette, NULL); LOGDXERR(LastError); LastError = destSurface->SetPalette(destPalette); LastError = tempSurface->SetPalette(destPalette); LOGDXERR(LastError); { memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = tempSurface->Lock(NULL, &ddsd, 0, NULL); LOGDXERR(LastError); unsigned char *dst = (unsigned char *)ddsd.lpSurface; LOCALASSERT(dst); for(int i = 0; i < 256; i ++) { for(int j = 0; j < 256; j ++) { int c = FastRandom()&255; *dst++ = (c); } /* move the pitch to width difference */ //dst += ddsd.lPitch - 256; } LastError = tempSurface->Unlock(NULL); LOGDXERR(LastError); } } else { { memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = tempSurface->Lock(NULL, &ddsd, 0, NULL); LOGDXERR(LastError); unsigned short *dst = (unsigned short *)ddsd.lpSurface; LOCALASSERT(dst); for(int i = 0; i < 256; i ++) { int density = FastRandom()&31; { for(int j = 0; j < 256; j ++) { int c = FastRandom()&31; *dst++ = (c)+(c<<6)+(c<<11); } } /* move the pitch to width difference */ //dst += ddsd.lPitch - 256; } LastError = tempSurface->Unlock(NULL); LOGDXERR(LastError); } } } LastError = destSurface->QueryInterface(IID_IDirect3DTexture,(LPVOID*) &destTexture); LOGDXERR(LastError); LastError = destTexture->Load(tempTexture); LOGDXERR(LastError); // Clean up surfaces etc // RELEASE(SrcTexture); LastError = destTexture->GetHandle(d3d.lpD3DDevice, &NoiseTextureHandle); RELEASE(tempSurface); RELEASE(tempTexture); } void DrawNoiseOverlay(int t) { // return; { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; extern float CameraZoomScale; float u = FastRandom()&255; float v = FastRandom()&255; int c = 255; int size = 256;//*CameraZoomScale; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = u/256.0; vertexPtr->tv = v/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = (u+size)/256.0; vertexPtr->tv = v/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = (u+size)/256.0; vertexPtr->tv = (v+size)/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = u/256.0; vertexPtr->tv = (v+size)/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_ALWAYS, ExecBufInstPtr); NoiseTextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[StaticImageNumber].D3DHandle; if (CurrTextureHandle != NoiseTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NoiseTextureHandle, ExecBufInstPtr); CurrTextureHandle = NoiseTextureHandle; } if (D3DTexturePerspective != No) { D3DTexturePerspective = No; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, FALSE, ExecBufInstPtr); } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } void DrawScanlinesOverlay(float level) { // return; { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float u = 0.0f;//FastRandom()&255; float v = 128.0f;//FastRandom()&255; int c = 255; extern float CameraZoomScale; int t; f2i(t,64.0f+level*64.0f); float size = 128.0f*(1.0f-level*0.8f);//*CameraZoomScale; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = (v-size)/256.0f; vertexPtr->tv = 1.0f; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = (v-size)/256.0f; vertexPtr->tv = 1.0f; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = (v+size)/256.0f; vertexPtr->tv = 1.0f; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->tu = (v+size)/256.0f; vertexPtr->tv = 1.0f; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,t); NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_ALWAYS, ExecBufInstPtr); NoiseTextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[PredatorNumbersImageNumber].D3DHandle; if (CurrTextureHandle != NoiseTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NoiseTextureHandle, ExecBufInstPtr); CurrTextureHandle = NoiseTextureHandle; } if (D3DTexturePerspective != No) { D3DTexturePerspective = No; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, FALSE, ExecBufInstPtr); } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } if (level==1.0f) DrawNoiseOverlay(128); } void DrawPredatorVisionChangeOverlay(int time) { // return; { if (time>ONE_FIXED) for(int i=0; i<8; i++) { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; int t = (time-ONE_FIXED-((i+3)&7)*2048)*2; if (t<0) t = 0; float rightU; float leftU; if (t>ONE_FIXED) { leftU = 0.0f; rightU = 0.5f; } else if (t>ONE_FIXED/2) { leftU = 1.0f - ((float)(t))/65536.0f; rightU = 1.0f - ((float)(t-ONE_FIXED/2))/65536.0f; } else { leftU = 1.0f - ((float)(t))/65536.0f; rightU = 1.0f; } float topV = 44.0f/128.0f; float bottomV = 119.0f/128.0f; if (leftU<0) leftU=0; PrintDebuggingText("%f %f\n",leftU,rightU); int rightX = MUL_FIXED((Global_VDB_Ptr->VDB_ClipRight-Global_VDB_Ptr->VDB_ClipLeft),t)+Global_VDB_Ptr->VDB_ClipLeft; if (rightX>Global_VDB_Ptr->VDB_ClipRight) rightX = Global_VDB_Ptr->VDB_ClipRight; int y = i*60; int h = 60;//+MUL_FIXED(10,time-ONE_FIXED); int c = 255; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = y; vertexPtr->sz = 0; vertexPtr->rhw = 1.0f; vertexPtr->tu = leftU; vertexPtr->tv = topV; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = rightX; vertexPtr->sy = y; vertexPtr->sz = 0; vertexPtr->rhw = 1.0f; vertexPtr->tu = rightU; vertexPtr->tv = topV; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = rightX; vertexPtr->sy = y+h; vertexPtr->sz = 0; vertexPtr->rhw = 1.0f; vertexPtr->tu = rightU; vertexPtr->tv = bottomV; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = y+h; vertexPtr->sz = 0; vertexPtr->rhw = 1.0f; vertexPtr->tu = leftU; vertexPtr->tv = bottomV; vertexPtr->color = RGBALIGHT_MAKE(255,255,255,255); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); NumVertices+=4; CheckTranslucencyModeIsCorrect(TRANSLUCENCY_COLOUR); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); // NoiseTextureHandle = 0; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[PredatorVisionChangeImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } } { if (time>ONE_FIXED+8192) time = ONE_FIXED+8192; { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float rightU = 1.0f; float leftU = 1.0f - ((float)time)/65536.0f; float v = 0; if (leftU<0) leftU=0; PrintDebuggingText("%f %f\n",leftU,rightU); int rightX = MUL_FIXED((Global_VDB_Ptr->VDB_ClipRight-Global_VDB_Ptr->VDB_ClipLeft),time)+Global_VDB_Ptr->VDB_ClipLeft; int c=128; int size = 256/4; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0.001; vertexPtr->rhw = 1.0f; vertexPtr->tu = leftU; vertexPtr->tv = v/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = 0; vertexPtr++; vertexPtr->sx = rightX; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0.001; vertexPtr->rhw = 1.0f; vertexPtr->tu = rightU; vertexPtr->tv = v/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = 0; vertexPtr++; vertexPtr->sx = rightX; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0.001; vertexPtr->rhw = 1.0f; vertexPtr->tu = rightU; vertexPtr->tv = (v+size)/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = 0; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0.001; vertexPtr->rhw = 1.0f; vertexPtr->tu = leftU; vertexPtr->tv = (v+size)/256.0; vertexPtr->color = RGBALIGHT_MAKE(c,c,c,255); vertexPtr->specular = 0; NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); // NoiseTextureHandle = 0; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[PredatorVisionChangeImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } } #if 0 #define OCTAVES 1 float u[OCTAVES]; float v[OCTAVES]; float du[OCTAVES]; float dv[OCTAVES]; int setup=0; void DrawFBM(void) { extern int CloudyImageNumber; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[CloudyImageNumber].D3DHandle; // return; 1 int i; int size = 256; // float u = FastRandom()&255; // float v = FastRandom()&255; int t =255; if(!setup) { setup=1; for(i=OCTAVES-1;i>=0;i--) { du[i] = ( (float)((FastRandom()&65535)-32768)*(i+1) )/16384.0; dv[i] = ( (float)((FastRandom()&65535)-32768)*(i+1) )/16384.0; } } float timeScale = ((float)NormalFrameTime)/65536.0; for(i=0; iVDB_Mat); VECTORCH v[4]= { {-ONE_FIXED,-ONE_FIXED,ONE_FIXED}, { ONE_FIXED,-ONE_FIXED,ONE_FIXED}, { ONE_FIXED, 0, ONE_FIXED}, {-ONE_FIXED, 0, ONE_FIXED}, }; TransposeMatrixCH(&mat); RotateVector(&v[0],&mat); RotateVector(&v[1],&mat); RotateVector(&v[2],&mat); RotateVector(&v[3],&mat); if (v[0].vy=0) v[0].vy=-1; if (v[1].vy=0) v[1].vy=-1; if (v[2].vy=0) v[2].vy=-1; if (v[3].vy=0) v[3].vy=-1; if (v[0].vy>0) v[0].vy=-v[0].vy; if (v[1].vy>0) v[1].vy=-v[1].vy; if (v[2].vy>0) v[2].vy=-v[2].vy; if (v[3].vy>0) v[3].vy=-v[3].vy; D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1; vertexPtr->tu = -((float)v[0].vx)/((float)v[0].vy)/1.0; vertexPtr->tv = -((float)v[0].vz)/((float)v[0].vy)/1.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1; vertexPtr->tu = -((float)v[1].vx)/((float)v[1].vy)/1.0; vertexPtr->tv = -((float)v[1].vz)/((float)v[1].vy)/1.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = (Global_VDB_Ptr->VDB_ClipUp+Global_VDB_Ptr->VDB_ClipDown)/2; vertexPtr->sz = 1; vertexPtr->tu = -((float)v[2].vx)/((float)v[2].vy)/1.0; vertexPtr->tv = -((float)v[2].vz)/((float)v[2].vy)/1.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = (Global_VDB_Ptr->VDB_ClipUp+Global_VDB_Ptr->VDB_ClipDown)/2; vertexPtr->sz = 1; vertexPtr->tu = -((float)v[3].vx)/((float)v[3].vy)/1.0; vertexPtr->tv = -((float)v[3].vz)/((float)v[3].vy)/1.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); NumVertices+=4; } #else { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1; vertexPtr->tu = u[i]/256.0; vertexPtr->tv = v[i]/256.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1; vertexPtr->tu = (u[i]+size)/256.0; vertexPtr->tv = v[i]/256.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1; vertexPtr->tu = (u[i]+size)/256.0; vertexPtr->tv = (v[i]+size)/256.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1; vertexPtr->tu = u[i]/256.0; vertexPtr->tv = (v[i]+size)/256.0; vertexPtr->color = RGBALIGHT_MAKE(200,255,255,t); vertexPtr->specular = RGBALIGHT_MAKE(0,0,0,255); NumVertices+=4; } #endif size*=2; t/=2; CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); // NoiseTextureHandle = 0; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = NoiseTextureHandle; } if (D3DTexturePerspective != No) { D3DTexturePerspective = No; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, FALSE, ExecBufInstPtr); } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } } #endif void D3D_SkyPolygon_Output(POLYHEADER *inputPolyPtr,RENDERVERTEX *renderVerticesPtr) { int flags; int texoffset; D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; // Get ZNear ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); // Take header information flags = inputPolyPtr->PolyFlags; // We assume bit 15 (TxLocal) HAS been // properly cleared this time... texoffset = (inputPolyPtr->PolyColour & ClrTxDefn); TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[texoffset].D3DHandle; // Check for textures that have not loaded // properly // if (TextureHandle == (D3DTEXTUREHANDLE) 0) // return; #ifdef AVP_DEBUG_VERSION if(ImageHeaderArray[texoffset].ImageWidth==128) { RecipW = (1.0 /128.0)/65536.0f; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width)/65536.0f; } if(ImageHeaderArray[texoffset].ImageHeight==128) { RecipH = (1.0 / 128.0)/65536.0f; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height)/65536.0f; } #else RecipW = (1.0/65536.0)/128.0; RecipH = (1.0/65536.0)/128.0; #endif // RecipW = (1.0/65536.0)/(float) ImageHeaderArray[texoffset].ImageWidth; // RecipH = (1.0/65536.0)/(float) ImageHeaderArray[texoffset].ImageHeight; /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/(vertices->Z); float zvalue; vertexPtr->tu = ((float)vertices->U) * RecipW + (1.0/256.0); vertexPtr->tv = ((float)vertices->V) * RecipH + (1.0/256.0); vertexPtr->rhw = oneOverZ; { zvalue = vertices->Z+HeadUpDisplayZOffset; // zvalue /= 65536.0; zvalue = 1.0 - ZNear/zvalue; } { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; #if 1 if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } #endif vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; #if 1 if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } #endif vertexPtr->sy=y; } // vertexPtr->tu = ((float)(vertices->U>>16)+0.5) * RecipW; // vertexPtr->tv = ((float)(vertices->V>>16)+0.5) * RecipH; // vertexPtr->rhw = oneOverZ; vertexPtr->color = RGBALIGHT_MAKE(vertices->R,vertices->G,vertices->B,vertices->A); vertexPtr->sz = 1.0; vertexPtr->specular=RGBALIGHT_MAKE(0,0,0,255); vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(RenderPolygon.TranslucencyMode); // Insert state change for shading model if required if (D3DShadingMode != D3DSHADE_GOURAUD) { D3DShadingMode = D3DSHADE_GOURAUD; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_SHADEMODE, D3DSHADE_GOURAUD, ExecBufInstPtr); } // Insert state change for texturing perspective value // Note that drawtx3das2d options have ONLY been allowed for here, // not when the rhw values are generated. This is a deliberate choice, // based on the assumption that drawtx3das2d will not be used very often // and the extra branching at the top of this function will impose a // greater cost than the (rare) savings in floating pt divisions are worth. // Or so I claim... if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } #if FMV_EVERYWHERE TextureHandle = FMVTextureHandle[0]; #endif if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } D3D_OutputTriangles(); } void D3D_DrawFMVOnWater(int xOrigin, int yOrigin, int zOrigin) { int colour; switch (CurrentVisionMode) { default: case VISION_MODE_NORMAL: { colour = RGBLIGHT_MAKE(128,128,128); break; } case VISION_MODE_IMAGEINTENSIFIER: { colour = RGBLIGHT_MAKE(0,255,0); break; } case VISION_MODE_PRED_THERMAL: case VISION_MODE_PRED_SEEALIENS: case VISION_MODE_PRED_SEEPREDTECH: { colour = RGBLIGHT_MAKE(128,0,128); break; } } int i=0; int x; for (x=0; x<16; x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; point->vz = zOrigin + (z*MeshZScale)/15; point->vz += (FastRandom()&31); point->vx = (x*MeshXScale)/15; point->vx -= MeshXScale/2; point->vx = (point->vx * (32-z))/16 + (FastRandom()&31); point->vx += xOrigin + MeshXScale/2; int offset = EffectOfRipples(point); point->vy = yOrigin+offset; { int alpha = 192-offset*4; if (alpha>255) alpha = 255; if (alpha<128) alpha = 128; MeshVertexColour[i] = colour + (alpha<<24); } #if 1 TranslatePointIntoViewspace(point); #else point->vx -= Global_VDB_Ptr->VDB_World.vx; point->vy -= Global_VDB_Ptr->VDB_World.vy; point->vz -= Global_VDB_Ptr->VDB_World.vz; MeshWorldVertex[i] = *point; RotateVector(point,&(Global_VDB_Ptr->VDB_Mat)); point->vy = MUL_FIXED(point->vy,87381); #endif /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } { // u MeshWorldVertex[i].vx = (x*4096)/15; // v MeshWorldVertex[i].vy = (z*2048)/20; } i++; } } D3DTEXTUREHANDLE TextureHandle = FMVTextureHandle[0]; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawMoltenMetalMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawMoltenMetalMesh_Clipped(); } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); } void D3D_DrawMoltenMetal(int xOrigin, int yOrigin, int zOrigin) { int i=0; int x; for (x=0; x<16; x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; point->vx = xOrigin+(x*MeshXScale)/15; point->vz = zOrigin+(z*MeshZScale)/15; #if 0 int offset=0; offset = MUL_FIXED(32,GetSin( (point->vx+point->vz+CloakingPhase)&4095 ) ); offset += MUL_FIXED(16,GetSin( (point->vx-point->vz*2+CloakingPhase/2)&4095 ) ); { float dx=point->vx-22704; float dz=point->vz+20652; float a = dx*dx+dz*dz; a=sqrt(a); offset+= MUL_FIXED(200,GetSin( (((int)a-CloakingPhase)&4095) )); } #endif #if 1 int offset=0; /* basic noise ripples */ offset = MUL_FIXED(128,GetSin( ((point->vx+point->vz)/16+CloakingPhase)&4095 ) ); offset += MUL_FIXED(64,GetSin( ((point->vx-point->vz*2)/4+CloakingPhase/2)&4095 ) ); offset += MUL_FIXED(64,GetSin( ((point->vx*5-point->vz)/32+CloakingPhase/5)&4095 ) ); #endif if (offset>450) offset = 450; if (offset<-1000) offset = -1000; point->vy = yOrigin+offset; { int shade = 191+(offset+256)/8; MeshVertexColour[i] = RGBLIGHT_MAKE(shade,shade,shade); } #if 1 TranslatePointIntoViewspace(point); #else point->vx -= Global_VDB_Ptr->VDB_World.vx; point->vy -= Global_VDB_Ptr->VDB_World.vy; point->vz -= Global_VDB_Ptr->VDB_World.vz; MeshWorldVertex[i] = *point; RotateVector(point,&(Global_VDB_Ptr->VDB_Mat)); point->vy = MUL_FIXED(point->vy,87381); #endif /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } #if 0 { // v MeshWorldVertex[i].vy = (offset+256)*4; // u MeshWorldVertex[i].vx = ((MeshWorldVertex[i].vx)&4095); } #else { Normalise(&MeshWorldVertex[i]); // v int theta = (MeshWorldVertex[i].vy+offset); if (theta<0) theta=0; if (theta>ONE_FIXED) theta=ONE_FIXED; // u int arctan = ((atan2((double)MeshWorldVertex[i].vx,(double)MeshWorldVertex[i].vz)/ 6.28318530718))*4095; MeshWorldVertex[i].vx = (arctan+offset)&4095; MeshWorldVertex[i].vy = ArcCos(theta); } #endif i++; } } D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[StaticImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawMoltenMetalMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawMoltenMetalMesh_Clipped(); } } void D3D_DrawMoltenMetalMesh_Unclipped(void) { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; VECTORCH *point = MeshVertex; VECTORCH *pointWS = MeshWorldVertex; int i; for (i=0; i<256; i++) { if (point->vz<=1) point->vz = 1; int x = (point->vx*(Global_VDB_Ptr->VDB_ProjX+1))/point->vz+Global_VDB_Ptr->VDB_CentreX; int y = (point->vy*(Global_VDB_Ptr->VDB_ProjY+1))/point->vz+Global_VDB_Ptr->VDB_CentreY; // textprint("%d, %d\n",x,y); #if 1 { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } #else vertexPtr->sx=x; vertexPtr->sy=y; #endif point->vz+=HeadUpDisplayZOffset; float oneOverZ = ((float)(point->vz)-ZNear)/(float)(point->vz); vertexPtr->color = MeshVertexColour[i]; vertexPtr->specular = 0; vertexPtr->sz = oneOverZ; vertexPtr->tu = pointWS->vx*WaterUScale+(1.0f/256.0f); vertexPtr->tv = pointWS->vy*WaterVScale+(1.0f/256.0f); vertexPtr->rhw = 1.0/point->vz; NumVertices++; vertexPtr++; point++; pointWS++; } } // textprint("numvertices %d\n",NumVertices); /* * Make sure that the triangle data (not OP) will be QWORD aligned */ if (QWORD_ALIGNED(ExecBufInstPtr)) { OP_NOP(ExecBufInstPtr); } OP_TRIANGLE_LIST(450, ExecBufInstPtr); /* CONSTRUCT POLYS */ { int x; for (x=0; x<15; x++) { int y; for(y=0; y<15; y++) { OUTPUT_TRIANGLE(0+x+(16*y),1+x+(16*y),16+x+(16*y), 256); OUTPUT_TRIANGLE(1+x+(16*y),17+x+(16*y),16+x+(16*y), 256); } } } #if 1 { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } #endif } void D3D_DrawMoltenMetalMesh_Clipped(void) { float ZNear = (float) (Global_VDB_Ptr->VDB_ClipZ * GlobalScale); /* OUTPUT VERTICES TO EXECUTE BUFFER */ { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; VECTORCH *point = MeshVertex; VECTORCH *pointWS = MeshWorldVertex; int i; for (i=0; i<256; i++) { { int z = point->vz; if (z<=0) z = 1; int x = (point->vx*(Global_VDB_Ptr->VDB_ProjX+1))/z+Global_VDB_Ptr->VDB_CentreX; int y = (point->vy*(Global_VDB_Ptr->VDB_ProjY+1))/z+Global_VDB_Ptr->VDB_CentreY; #if 1 { if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } #else vertexPtr->sx=x; vertexPtr->sy=y; #endif vertexPtr->tu = pointWS->vx*WaterUScale+(1.0f/256.0f); vertexPtr->tv = pointWS->vy*WaterVScale+(1.0f/256.0f); point->vz+=HeadUpDisplayZOffset; float oneOverZ = ((float)(z)-ZNear)/(float)(z); vertexPtr->color = MeshVertexColour[i]; vertexPtr->specular = 0; vertexPtr->sz = oneOverZ; vertexPtr->rhw = 1.0f/(float)z; } NumVertices++; vertexPtr++; point++; pointWS++; } } // textprint("numvertices %d\n",NumVertices); /* CONSTRUCT POLYS */ { // OP_TRIANGLE_LIST(450, ExecBufInstPtr); int x; for (x=0; x<15; x++) { int y; for(y=0; y<15; y++) { int p1 = 0+x+(16*y); int p2 = 1+x+(16*y); int p3 = 16+x+(16*y); int p4 = 17+x+(16*y); #if 0 if (MeshVertexOutcode[p1]&&MeshVertexOutcode[p2]&&MeshVertexOutcode[p3]) { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(p1,p2,p3, 256); } if (MeshVertexOutcode[p2]&&MeshVertexOutcode[p3]&&MeshVertexOutcode[p4]) { OP_TRIANGLE_LIST(1, ExecBufInstPtr); OUTPUT_TRIANGLE(p2,p4,p3, 256); } #else if (MeshVertexOutcode[p1]&&MeshVertexOutcode[p2]&&MeshVertexOutcode[p3]&&MeshVertexOutcode[p4]) { OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(p1,p2,p3, 256); OUTPUT_TRIANGLE(p2,p4,p3, 256); } #endif } } } #if 1 { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } #endif #if 1 { // OP_TRIANGLE_LIST(450, ExecBufInstPtr); POLYHEADER fakeHeader; fakeHeader.PolyFlags = 0; fakeHeader.PolyColour = 0; RenderPolygon.TranslucencyMode = TRANSLUCENCY_NORMAL; int x; for (x=0; x<15; x++) { int y; for(y=0; y<15; y++) { int p[4]; p[0] = 0+x+(16*y); p[1] = 1+x+(16*y); p[2] = 17+x+(16*y); p[3] = 16+x+(16*y); if (!(MeshVertexOutcode[p[0]]&&MeshVertexOutcode[p[1]]&&MeshVertexOutcode[p[2]]&&MeshVertexOutcode[p[3]])) { { int i; for (i=0; i<4; i++) { VerticesBuffer[i].X = MeshVertex[p[i]].vx; VerticesBuffer[i].Y = MeshVertex[p[i]].vy; VerticesBuffer[i].Z = MeshVertex[p[i]].vz; VerticesBuffer[i].U = MeshWorldVertex[p[i]].vx*(WaterUScale*128.0f*65536.0f); VerticesBuffer[i].V = MeshWorldVertex[p[i]].vy*(WaterVScale*128.0f*65536.0f); VerticesBuffer[i].A = (MeshVertexColour[p[i]]&0xff000000)>>24; VerticesBuffer[i].R = (MeshVertexColour[p[i]]&0x00ff0000)>>16; VerticesBuffer[i].G = (MeshVertexColour[p[i]]&0x0000ff00)>>8; VerticesBuffer[i].B = MeshVertexColour[p[i]]&0x000000ff; VerticesBuffer[i].SpecularR = 0; VerticesBuffer[i].SpecularG = 0; VerticesBuffer[i].SpecularB = 0; } RenderPolygon.NumberOfVertices=4; } { int outcode = QuadWithinFrustrum(); if (outcode) { GouraudTexturedPolygon_ClipWithZ(); if(RenderPolygon.NumberOfVertices<3) continue; GouraudTexturedPolygon_ClipWithNegativeX(); if(RenderPolygon.NumberOfVertices<3) continue; GouraudTexturedPolygon_ClipWithPositiveY(); if(RenderPolygon.NumberOfVertices<3) continue; GouraudTexturedPolygon_ClipWithNegativeY(); if(RenderPolygon.NumberOfVertices<3) continue; GouraudTexturedPolygon_ClipWithPositiveX(); if(RenderPolygon.NumberOfVertices<3) continue; // D3D_ZBufferedGouraudPolygon_Output(&fakeHeader,RenderPolygon.Vertices); D3D_ZBufferedGouraudTexturedPolygon_Output(&fakeHeader,RenderPolygon.Vertices); } } } } } } #endif #if 1 { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } #endif } void *DynamicImagePtr; #define NUMBER_OF_SMACK_SURFACES 4 LPDIRECTDRAWSURFACE SrcDDSurface[NUMBER_OF_SMACK_SURFACES]; LPDIRECT3DTEXTURE SrcTexture[NUMBER_OF_SMACK_SURFACES]; void *SrcSurfacePtr[NUMBER_OF_SMACK_SURFACES]; LPDIRECTDRAWSURFACE DstDDSurface[NUMBER_OF_SMACK_SURFACES]={0,0,0}; LPDIRECT3DTEXTURE DstTexture[NUMBER_OF_SMACK_SURFACES]={0,0,0}; int CurrentSurface; void InitDrawTest(void) { #if FMV_ON DDSURFACEDESC ddsd; int surface = NUMBER_OF_SMACK_SURFACES; while(surface--) { memcpy(&ddsd, &(d3d.TextureFormat[d3d.CurrentTextureFormat].ddsd), sizeof(ddsd)); ddsd.dwSize = sizeof(ddsd); ddsd.dwFlags = (DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT); ddsd.ddsCaps.dwCaps = (DDSCAPS_SYSTEMMEMORY|DDSCAPS_TEXTURE); ddsd.dwHeight = FMV_SIZE; ddsd.dwWidth = FMV_SIZE; LastError = lpDD->CreateSurface(&ddsd, &SrcDDSurface[surface], NULL); LOGDXERR(LastError); DDBLTFX ddbltfx; memset(&ddbltfx, 0, sizeof(ddbltfx)); ddbltfx.dwSize = sizeof(ddbltfx); ddbltfx.dwFillColor = 0;// (2<<11)+(26<<5)+8; LastError=SrcDDSurface[surface]->Blt(NULL, NULL, NULL, DDBLT_COLORFILL | DDBLT_WAIT, &ddbltfx); LOGDXERR(LastError); LastError = SrcDDSurface[surface]->QueryInterface(IID_IDirect3DTexture, (LPVOID*) &SrcTexture[surface]); LOGDXERR(LastError); { int PalCaps; if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { PalCaps = (DDPCAPS_8BIT | DDPCAPS_ALLOW256); } else if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED4) { PalCaps = DDPCAPS_4BIT; } else { PalCaps = 0; } if (PalCaps) { LPDIRECTDRAWPALETTE destPalette = NULL; LastError = lpDD->CreatePalette(PalCaps, FMVPalette[surface], &destPalette, NULL); LOGDXERR(LastError); LastError = SrcDDSurface[surface]->SetPalette(destPalette); // LastError = tempSurface->SetPalette(destPalette); LOGDXERR(LastError); } } memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = SrcDDSurface[surface]->Lock(NULL,&ddsd,0,NULL); LOGDXERR(LastError); SrcSurfacePtr[surface] = (void*)ddsd.lpSurface; LastError = SrcDDSurface[surface]->Unlock(NULL); LOGDXERR(LastError); } CurrentSurface=0; { extern void InitFMV(void); InitFMV(); } FMVTextureHandle[0]=0; FMVTextureHandle[1]=0; FMVTextureHandle[2]=0; #endif } void D3D_DrawFMV(int xOrigin, int yOrigin, int zOrigin) { MeshXScale = 4096/8/3; MeshZScale = 4096/8/3; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); for (int field=0; field<3; field++) { for (int zfield=0; zfield<3; zfield++) { int i=0; int x; for (x=(0+field*15); x<(16+field*15); x++) { int z; for(z=0+zfield*15; z<16+zfield*15; z++) { VECTORCH *point = &MeshVertex[i]; point->vx = xOrigin+(x*MeshXScale); point->vy = yOrigin+(z*MeshZScale); int offset; offset = MUL_FIXED(128,GetSin( ((point->vx+point->vy)+CloakingPhase)&4095 ) ); offset += MUL_FIXED(64,GetSin( ((point->vx-point->vy*2)+CloakingPhase/2)&4095 ) ); offset += MUL_FIXED(64,GetSin( ((point->vx*5-point->vy)/2+CloakingPhase/5)&4095 ) ); point->vz = zOrigin+offset; { int shade = 127+(offset+256)/4; MeshVertexColour[i] = RGBALIGHT_MAKE(shade,shade,shade,192); } #if 0 { int sd; int size=65536; int theta = ((z*4096)/45)&4095; int phi = ((x*2048)/45)&4095; if (theta==0) sd = 0; else sd = phi+theta; if (phi==0 || phi==2048) sd = 0; else sd = phi+theta; int outerRadius = MUL_FIXED(4000+offset,size); if (sd) offset = MUL_FIXED((FastRandom()&511)-255,size); offset=0; point->vx = xOrigin+2000+MUL_FIXED(outerRadius+offset,MUL_FIXED(GetSin(theta),GetCos(phi))); point->vy = yOrigin+MUL_FIXED(outerRadius+offset,MUL_FIXED(GetSin(theta),GetSin(phi))); point->vz = zOrigin+MUL_FIXED(outerRadius+offset,GetCos(theta)); } #endif MeshWorldVertex[i].vx = (x*4096/45); MeshWorldVertex[i].vy = (z*2048/45); TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } //textprint("\n"); D3DTEXTUREHANDLE TextureHandle = FMVTextureHandle[0]; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL);//GLOWING); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawMoltenMetalMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawMoltenMetalMesh_Clipped(); } } } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); } void RenderFMVParticle(int t, int o, VECTORCH *offsetPtr) { { VECTORCH translatedPosition = MeshVertex[o+t]; translatedPosition.vx += offsetPtr->vx; translatedPosition.vy += offsetPtr->vy; translatedPosition.vz += offsetPtr->vz; TranslatePointIntoViewspace(&translatedPosition); VerticesBuffer[0].X = translatedPosition.vx; VerticesBuffer[0].Y = translatedPosition.vy; VerticesBuffer[0].Z = translatedPosition.vz; } { VECTORCH translatedPosition = MeshVertex[1+t]; translatedPosition.vx += offsetPtr->vx; translatedPosition.vy += offsetPtr->vy; translatedPosition.vz += offsetPtr->vz; TranslatePointIntoViewspace(&translatedPosition); VerticesBuffer[1].X = translatedPosition.vx; VerticesBuffer[1].Y = translatedPosition.vy; VerticesBuffer[1].Z = translatedPosition.vz; } { VECTORCH translatedPosition = MeshVertex[16+t]; translatedPosition.vx += offsetPtr->vx; translatedPosition.vy += offsetPtr->vy; translatedPosition.vz += offsetPtr->vz; TranslatePointIntoViewspace(&translatedPosition); VerticesBuffer[2].X = translatedPosition.vx; VerticesBuffer[2].Y = translatedPosition.vy; VerticesBuffer[2].Z = translatedPosition.vz; } { int outcode = TriangleWithinFrustrum(); if (outcode) { /* setup */ RenderPolygon.NumberOfVertices=3; VerticesBuffer[0].U = MeshWorldVertex[o+t].vx; VerticesBuffer[0].V = MeshWorldVertex[o+t].vy; VerticesBuffer[0].A = 192; VerticesBuffer[1].U = MeshWorldVertex[1+t].vx; VerticesBuffer[1].V = MeshWorldVertex[1+t].vy; VerticesBuffer[1].A = 192; VerticesBuffer[2].U = MeshWorldVertex[16+t].vx; VerticesBuffer[2].V = MeshWorldVertex[16+t].vy; VerticesBuffer[2].A = 192; if (outcode!=2) { TexturedPolygon_ClipWithZ(); if(RenderPolygon.NumberOfVertices<3) return; TexturedPolygon_ClipWithNegativeX(); if(RenderPolygon.NumberOfVertices<3) return; TexturedPolygon_ClipWithPositiveY(); if(RenderPolygon.NumberOfVertices<3) return; TexturedPolygon_ClipWithNegativeY(); if(RenderPolygon.NumberOfVertices<3) return; TexturedPolygon_ClipWithPositiveX(); if(RenderPolygon.NumberOfVertices<3) return; D3D_FMVParticle_Output(RenderPolygon.Vertices); } else D3D_FMVParticle_Output(VerticesBuffer); } } } void D3D_DrawSwirlyFMV(int xOrigin, int yOrigin, int zOrigin) { MeshXScale = 2048/8; MeshZScale = (2048*3)/8/4; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); int i=0; int x; for (x=0; x<16; x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; point->vz = zOrigin+(x*MeshXScale); point->vy = yOrigin+(z*MeshZScale); int offset; offset = MUL_FIXED(128,GetSin( ((point->vz+point->vy)+CloakingPhase)&4095 ) ); offset += MUL_FIXED(64,GetSin( ((point->vz-point->vy*2)+CloakingPhase/2)&4095 ) ); offset += MUL_FIXED(64,GetSin( ((point->vz*5-point->vy)/2+CloakingPhase/5)&4095 ) ); point->vx = xOrigin+offset; MeshWorldVertex[i].vx = ((15-x)*65536*128)/15; MeshWorldVertex[i].vy = (z*49152*128)/15; i++; } } for (x=0; x<15; x++) { int y; for(y=0; y<15; y++) { int a = (x+y*15)*2; int b = 1; int o = x+y*16; int t = 0; do { int p = a+b; #if 1 RenderFMVParticle(o,t,&FMVParticlePosition[p]); #else { PARTICLE particle; particle.ParticleID = PARTICLE_NONCOLLIDINGFLAME; particle.Position = FMVParticleAbsPosition[p]; particle.Colour = RGBA_MAKE(255,255,255,16); particle.Size = 3000; RenderParticle(&particle); } #endif FMVParticleAbsPosition[p] = MeshVertex[o+t]; FMVParticleAbsPosition[p].vx += FMVParticlePosition[p].vx; FMVParticleAbsPosition[p].vy += FMVParticlePosition[p].vy; FMVParticleAbsPosition[p].vz += FMVParticlePosition[p].vz; t=17; } while(b--); } } for(int p=0; p<450; p++) { #if 0 if ((CloakingPhase&32767) > 16383) { int n=p+52; int o=p+76; if (n>449) n-=449; if (o>449) o-=449; FMVParticlePosition[p].vx -= MUL_FIXED(FMVParticleAbsPosition[p].vx - FMVParticleAbsPosition[n].vx,NormalFrameTime*8); FMVParticlePosition[p].vy -= MUL_FIXED(FMVParticleAbsPosition[p].vy - FMVParticleAbsPosition[n].vy,NormalFrameTime*8); FMVParticlePosition[p].vz -= MUL_FIXED(FMVParticleAbsPosition[p].vz - FMVParticleAbsPosition[n].vz,NormalFrameTime*8); FMVParticlePosition[p].vx += MUL_FIXED(FMVParticleAbsPosition[p].vx - FMVParticleAbsPosition[o].vx,NormalFrameTime/4); FMVParticlePosition[p].vy += MUL_FIXED(FMVParticleAbsPosition[p].vy - FMVParticleAbsPosition[o].vy,NormalFrameTime/4); FMVParticlePosition[p].vz += MUL_FIXED(FMVParticleAbsPosition[p].vz - FMVParticleAbsPosition[o].vz,NormalFrameTime/4); } else { FMVParticlePosition[p].vx -= MUL_FIXED(FMVParticlePosition[p].vx,NormalFrameTime*4); FMVParticlePosition[p].vy -= MUL_FIXED(FMVParticlePosition[p].vy,NormalFrameTime*4); FMVParticlePosition[p].vz -= MUL_FIXED(FMVParticlePosition[p].vz,NormalFrameTime*4); int m = Approximate3dMagnitude(&FMVParticlePosition[p]); if (m<=20) { FMVParticlePosition[p].vx = 0; FMVParticlePosition[p].vy = 0; FMVParticlePosition[p].vz = 0; } } #else FMVParticlePosition[p].vx = 0; FMVParticlePosition[p].vy = 0; FMVParticlePosition[p].vz = 0; #endif } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); } static void UpdateFMVTextures(int maxTextureNumberToUpdate) { #if FMV_ON int surfaceNumber=maxTextureNumberToUpdate; while(surfaceNumber--) { DDSURFACEDESC ddsd; memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = SrcDDSurface[surfaceNumber]->Lock(NULL,&ddsd,DDLOCK_WAIT,NULL); LOGDXERR(LastError); { if (!NextFMVFrame(SrcSurfacePtr[surfaceNumber],0,0,128,96, surfaceNumber)) { LastError = SrcDDSurface[surfaceNumber]->Unlock(NULL); LOGDXERR(LastError); return; } } LastError = SrcDDSurface[surfaceNumber]->Unlock(NULL); LOGDXERR(LastError); if (DstDDSurface[surfaceNumber]) ReleaseDDSurface(DstDDSurface[surfaceNumber]); if (DstTexture[surfaceNumber]) ReleaseD3DTexture(DstTexture[surfaceNumber]); // Query destination surface for a texture interface. memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = SrcDDSurface[surfaceNumber]->GetSurfaceDesc(&ddsd); LOGDXERR(LastError); ddsd.dwFlags = (DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT); ddsd.ddsCaps.dwCaps = (DDSCAPS_TEXTURE | DDSCAPS_ALLOCONLOAD ); LastError = lpDD->CreateSurface(&ddsd, &DstDDSurface[surfaceNumber], NULL); LOGDXERR(LastError); { int PalCaps; if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { PalCaps = (DDPCAPS_8BIT | DDPCAPS_ALLOW256); } else if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED4) { PalCaps = DDPCAPS_4BIT; } else { PalCaps = 0; } if (PalCaps) { LPDIRECTDRAWPALETTE destPalette = NULL; LastError = lpDD->CreatePalette(PalCaps, FMVPalette[surfaceNumber], &destPalette, NULL); LOGDXERR(LastError); UpdateFMVPalette(FMVPalette[surfaceNumber],surfaceNumber); LastError = DstDDSurface[surfaceNumber]->SetPalette(destPalette); LOGDXERR(LastError); LastError = SrcDDSurface[surfaceNumber]->SetPalette(destPalette); LOGDXERR(LastError); } } LastError = DstDDSurface[surfaceNumber]->QueryInterface(IID_IDirect3DTexture,(LPVOID*) &DstTexture[surfaceNumber]); LOGDXERR(LastError); LastError = DstTexture[surfaceNumber]->Load(SrcTexture[surfaceNumber]); LOGDXERR(LastError); LastError = DstTexture[surfaceNumber]->GetHandle(d3d.lpD3DDevice, &FMVTextureHandle[surfaceNumber]); LOGDXERR(LastError); } #endif } void KillFMVTexture(void) { int surface = NUMBER_OF_SMACK_SURFACES; while(surface--) { RELEASE(SrcDDSurface[surface]); RELEASE(SrcTexture[surface]); RELEASE(DstDDSurface[surface]); RELEASE(DstTexture[surface]); } } void ThisFramesRenderingHasBegun(void) { if (ScanDrawMode != ScanDrawDirectDraw) { BeginD3DScene(); LockExecuteBuffer(); D3D_SetupSceneDefaults(); } else { LockSurfaceAndGetBufferPointer(); } } void ThisFramesRenderingHasFinished(void) { if (ScanDrawMode != ScanDrawDirectDraw) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); EndD3DScene(); } /* KJL 11:46:56 01/16/97 - kill off any lights which are fated to be removed */ LightBlockDeallocation(); } void D3D_DrawWaterOctagonPatch(int xOrigin, int yOrigin, int zOrigin, int xOffset, int zOffset) { float grad = 2.414213562373; int i=0; int x; for (x=xOffset; x<16+xOffset; x++) { int z; for(z=zOffset; z<16+zOffset; z++) { VECTORCH *point = &MeshVertex[i]; if (x>z) { float m,xs; if (x!=0) { m = (float)(z)/(float)(x); xs = grad/(grad+m); } else { xs = 0; } #if 1 f2i(point->vx , xs*x*MeshXScale); f2i(point->vz , (grad-grad*xs)*x*MeshZScale); #else point->vx = xs*x*MeshXScale; point->vz = (grad-grad*xs)*x*MeshZScale; #endif } else { float m,xs; if (z!=0) { m = (float)(x)/(float)(z); xs = grad/(grad+m); } else { xs = 0; } #if 1 f2i(point->vz , xs*z*MeshZScale); f2i(point->vx , (grad-grad*xs)*z*MeshXScale); #else point->vz = xs*z*MeshZScale; point->vx = (grad-grad*xs)*z*MeshXScale; #endif } point->vx += xOrigin; point->vz += zOrigin; int offset = EffectOfRipples(point); point->vy = yOrigin+offset; #if 0 MeshVertexColour[i] = LightSourceWaterPoint(point,offset); #else { int alpha = 128-offset/4; // if (alpha>255) alpha = 255; // if (alpha<128) alpha = 128; switch (CurrentVisionMode) { default: case VISION_MODE_NORMAL: { MeshVertexColour[i] = RGBALIGHT_MAKE(10,51,28,alpha); break; } case VISION_MODE_IMAGEINTENSIFIER: { MeshVertexColour[i] = RGBALIGHT_MAKE(0,51,0,alpha); break; } case VISION_MODE_PRED_THERMAL: case VISION_MODE_PRED_SEEALIENS: case VISION_MODE_PRED_SEEPREDTECH: { MeshVertexColour[i] = RGBALIGHT_MAKE(0,0,28,alpha); break; } } } #endif TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawWaterMesh_Clipped(); } } extern void D3D_DrawSliderBar(int x, int y, int alpha) { struct VertexTag quadVertices[4]; int sliderHeight = 11; unsigned int colour = alpha>>8; if (colour>255) colour = 255; colour = (colour<<24)+0xffffff; quadVertices[0].Y = y; quadVertices[1].Y = y; quadVertices[2].Y = y + sliderHeight; quadVertices[3].Y = y + sliderHeight; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); { int topLeftU = 1; int topLeftV = 68; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 2; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 2; quadVertices[2].V = topLeftV + sliderHeight; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + sliderHeight; quadVertices[0].X = x; quadVertices[3].X = x; quadVertices[1].X = x + 2; quadVertices[2].X = x + 2; D3D_HUDQuad_Output ( HUDFontsImageNumber, quadVertices, colour ); } { int topLeftU = 7; int topLeftV = 68; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 2; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 2; quadVertices[2].V = topLeftV + sliderHeight; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + sliderHeight; quadVertices[0].X = x+213+2; quadVertices[3].X = x+213+2; quadVertices[1].X = x+2 +213+2; quadVertices[2].X = x+2 +213+2; D3D_HUDQuad_Output ( HUDFontsImageNumber, quadVertices, colour ); } quadVertices[2].Y = y + 2; quadVertices[3].Y = y + 2; { int topLeftU = 5; int topLeftV = 77; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU; quadVertices[2].V = topLeftV + 2; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 2; quadVertices[0].X = x + 2; quadVertices[3].X = x + 2; quadVertices[1].X = x + 215; quadVertices[2].X = x + 215; D3D_HUDQuad_Output ( HUDFontsImageNumber, quadVertices, colour ); } quadVertices[0].Y = y + 9; quadVertices[1].Y = y + 9; quadVertices[2].Y = y + 11; quadVertices[3].Y = y + 11; { int topLeftU = 5; int topLeftV = 77; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU; quadVertices[2].V = topLeftV + 2; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 2; quadVertices[0].X = x + 2; quadVertices[3].X = x + 2; quadVertices[1].X = x + 215; quadVertices[2].X = x + 215; D3D_HUDQuad_Output ( HUDFontsImageNumber, quadVertices, colour ); } } extern void D3D_DrawSlider(int x, int y, int alpha) { struct VertexTag quadVertices[4]; int sliderHeight = 5; unsigned int colour = alpha>>8; if (colour>255) colour = 255; colour = (colour<<24)+0xffffff; quadVertices[0].Y = y; quadVertices[1].Y = y; quadVertices[2].Y = y + sliderHeight; quadVertices[3].Y = y + sliderHeight; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); { int topLeftU = 11; int topLeftV = 74; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 9; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 9; quadVertices[2].V = topLeftV + sliderHeight; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + sliderHeight; quadVertices[0].X = x; quadVertices[3].X = x; quadVertices[1].X = x + 9; quadVertices[2].X = x + 9; D3D_HUDQuad_Output ( HUDFontsImageNumber, quadVertices, colour ); } } void DrawFontTest(void) { CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); struct VertexTag quadVertices[4]; quadVertices[0].Y = 0; quadVertices[1].Y = 0; quadVertices[2].Y = 256; quadVertices[3].Y = 256; quadVertices[0].U = 0; quadVertices[0].V = 0; quadVertices[1].U = 256; quadVertices[1].V = 0; quadVertices[2].U = 256; quadVertices[2].V = 256; quadVertices[3].U = 0; quadVertices[3].V = 256; quadVertices[0].X = 0; quadVertices[3].X = 0; quadVertices[1].X = 256; quadVertices[2].X = 256; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, 0xffffffff ); } extern void D3D_DrawRectangle(int x, int y, int w, int h, int alpha) { struct VertexTag quadVertices[4]; int sliderHeight = 11; unsigned int colour = alpha>>8; if (colour>255) colour = 255; colour = (colour<<24)+0xffffff; quadVertices[0].Y = y; quadVertices[1].Y = y; quadVertices[2].Y = y + 6; quadVertices[3].Y = y + 6; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); /* top left corner */ { int topLeftU = 1; int topLeftV = 238; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 6; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 6; quadVertices[2].V = topLeftV + 6; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 6; quadVertices[0].X = x; quadVertices[3].X = x; quadVertices[1].X = x + 6; quadVertices[2].X = x + 6; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } /* top */ { int topLeftU = 9; int topLeftV = 238; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU; quadVertices[2].V = topLeftV + 6; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 6; quadVertices[0].X = x+6; quadVertices[3].X = x+6; quadVertices[1].X = x+6 + w-12; quadVertices[2].X = x+6 + w-12; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } /* top right corner */ { int topLeftU = 11; int topLeftV = 238; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 6; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 6; quadVertices[2].V = topLeftV + 6; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 6; quadVertices[0].X = x + w - 6; quadVertices[3].X = x + w - 6; quadVertices[1].X = x + w; quadVertices[2].X = x + w; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } quadVertices[0].Y = y + 6; quadVertices[1].Y = y + 6; quadVertices[2].Y = y + h - 6; quadVertices[3].Y = y + h - 6; /* right */ { int topLeftU = 1; int topLeftV = 246; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 6; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 6; quadVertices[2].V = topLeftV; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } /* left */ { int topLeftU = 1; int topLeftV = 246; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 6; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 6; quadVertices[2].V = topLeftV; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV; quadVertices[0].X = x; quadVertices[3].X = x; quadVertices[1].X = x + 6; quadVertices[2].X = x + 6; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } quadVertices[0].Y = y + h - 6; quadVertices[1].Y = y + h - 6; quadVertices[2].Y = y + h; quadVertices[3].Y = y + h; /* bottom left corner */ { int topLeftU = 1; int topLeftV = 248; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 6; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 6; quadVertices[2].V = topLeftV + 6; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 6; quadVertices[0].X = x; quadVertices[3].X = x; quadVertices[1].X = x + 6; quadVertices[2].X = x + 6; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } /* bottom */ { int topLeftU = 9; int topLeftV = 238; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU; quadVertices[2].V = topLeftV + 6; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 6; quadVertices[0].X = x+6; quadVertices[3].X = x+6; quadVertices[1].X = x+6 + w-12; quadVertices[2].X = x+6 + w-12; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } /* bottom right corner */ { int topLeftU = 11; int topLeftV = 248; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + 6; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + 6; quadVertices[2].V = topLeftV + 6; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + 6; quadVertices[0].X = x + w - 6; quadVertices[3].X = x + w - 6; quadVertices[1].X = x + w; quadVertices[2].X = x + w; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } } extern void D3D_DrawColourBar(int yTop, int yBottom, int rScale, int gScale, int bScale) { extern unsigned char GammaValues[256]; CheckTranslucencyModeIsCorrect(TRANSLUCENCY_OFF); if (CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } for (int i=0; i<255; ) { { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; unsigned int colour; unsigned int c; c = GammaValues[i]; colour = RGBA_MAKE(MUL_FIXED(c,rScale),MUL_FIXED(c,gScale),MUL_FIXED(c,bScale),0); vertexPtr->sx = (Global_VDB_Ptr->VDB_ClipRight*i)/255; vertexPtr->sy = yTop; vertexPtr->sz = 0; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = (Global_VDB_Ptr->VDB_ClipRight*i)/255; vertexPtr->sy = yBottom; vertexPtr->sz = 0; vertexPtr->color = colour; vertexPtr++; i++; c = GammaValues[i]; colour = RGBA_MAKE(MUL_FIXED(c,rScale),MUL_FIXED(c,gScale),MUL_FIXED(c,bScale),0); vertexPtr->sx = (Global_VDB_Ptr->VDB_ClipRight*i)/255; vertexPtr->sy = yBottom; vertexPtr->sz = 0; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = (Global_VDB_Ptr->VDB_ClipRight*i)/255; vertexPtr->sy = yTop; vertexPtr->sz = 0; vertexPtr->color = colour; vertexPtr++; NumVertices+=4; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } } extern void D3D_FadeDownScreen(int brightness, int colour) { { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; int t = 255 - (brightness>>8); if (t<0) t = 0; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->color = (t<<24)+colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->color = (t<<24)+colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->color = (t<<24)+colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->color = (t<<24)+colour; NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_NORMAL); // CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); // NoiseTextureHandle = 0; if (CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } extern void ClearZBufferWithPolygon(void) { { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1; vertexPtr->color = 0; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1; vertexPtr->color = 0; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1; vertexPtr->color = 0; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1; vertexPtr->color = 0; NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_JUSTSETZ); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_ALWAYS, ExecBufInstPtr); D3DTEXTUREHANDLE TextureHandle = 0; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } extern void D3D_PlayerOnFireOverlay(void) { { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; int t = 128; int colour = (FMVParticleColour&0xffffff)+(t<<24); float u = (FastRandom()&255)/256.0f; float v = (FastRandom()&255)/256.0f; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = u; vertexPtr->tv = v; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = u+1.0f; vertexPtr->tv = v; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = u+1.0f; vertexPtr->tv = v+1.0f; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = u; vertexPtr->tv = v+1.0f; vertexPtr->color = colour; NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[BurningImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } extern void D3D_ScreenInversionOverlay(void) { int theta[2]; int colour = 0xffffffff; int i; theta[0] = (CloakingPhase/8)&4095; theta[1] = (800-CloakingPhase/8)&4095; CheckTranslucencyModeIsCorrect(TRANSLUCENCY_DARKENINGCOLOUR); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); for (i=0; i<2; i++) { float sin = (GetSin(theta[i]))/65536.0f/16.0f; float cos = (GetCos(theta[i]))/65536.0f/16.0f; { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = 0.375 + (cos*(-1) - sin*(-1)); vertexPtr->tv = 0.375 + (sin*(-1) + cos*(-1)); vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = .375 + (cos*(+1) - sin*(-1)); vertexPtr->tv = .375 + (sin*(+1) + cos*(-1)); vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = .375 + (cos*(+1) - sin*(+1)); vertexPtr->tv = .375 + (sin*(+1) + cos*(+1)); vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = .375 + (cos*(-1) - sin*(+1)); vertexPtr->tv = .375 + (sin*(-1) + cos*(+1)); vertexPtr->color = colour; NumVertices+=4; } // D3DTEXTUREHANDLE TextureHandle = NULL; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[SpecialFXImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_COLOUR); } } extern void D3D_PredatorScreenInversionOverlay(void) { int colour = 0xffffffff; int i; { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 1.0f; vertexPtr->rhw = 1.0f; vertexPtr->color = colour; NumVertices+=4; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_DARKENINGCOLOUR); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_ALWAYS, ExecBufInstPtr); // D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[StaticImageNumber].D3DHandle; D3DTEXTUREHANDLE TextureHandle = NULL; // D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[SpecialFXImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZFUNC, D3DCMP_LESSEQUAL, ExecBufInstPtr); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } } extern void D3D_PlayerDamagedOverlay(int intensity) { int theta[2]; // int colour = 0x00ffff + (intensity<<24); int colour,baseColour; int i; theta[0] = (CloakingPhase/8)&4095; theta[1] = (800-CloakingPhase/8)&4095; switch(AvP.PlayerType) { default: LOCALASSERT(0); /* if no debug then fall through to marine */ case I_Marine: baseColour = 0xff0000; break; case I_Alien: baseColour = 0xffff00; break; case I_Predator: baseColour = 0x00ff00; break; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_INVCOLOUR); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_ON); colour = 0xffffff - baseColour + (intensity<<24); for(i=0; i<=1; i++) { float sin = (GetSin(theta[i]))/65536.0f/16.0f; float cos = (GetCos(theta[i]))/65536.0f/16.0f; { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = 0.875 + (cos*(-1) - sin*(-1)); vertexPtr->tv = 0.375 + (sin*(-1) + cos*(-1)); vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipUp; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = .875 + (cos*(+1) - sin*(-1)); vertexPtr->tv = .375 + (sin*(+1) + cos*(-1)); vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipRight; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = .875 + (cos*(+1) - sin*(+1)); vertexPtr->tv = .375 + (sin*(+1) + cos*(+1)); vertexPtr->color = colour; vertexPtr++; vertexPtr->sx = Global_VDB_Ptr->VDB_ClipLeft; vertexPtr->sy = Global_VDB_Ptr->VDB_ClipDown; vertexPtr->sz = 0; vertexPtr->rhw = 1; vertexPtr->tu = .875 + (cos*(-1) - sin*(+1)); vertexPtr->tv = .375 + (sin*(-1) + cos*(+1)); vertexPtr->color = colour; NumVertices+=4; } // D3DTEXTUREHANDLE TextureHandle = NULL; D3DTEXTUREHANDLE TextureHandle = (D3DTEXTUREHANDLE)ImageHeaderArray[SpecialFXImageNumber].D3DHandle; if (CurrTextureHandle != TextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } // colour = 0xff0000+(intensity<<24); colour = baseColour +(intensity<<24); CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); } } #define NUMBER_OF_CABLE_SEGMENTS 25 int CableTheta[NUMBER_OF_CABLE_SEGMENTS]; int CablePhi[NUMBER_OF_CABLE_SEGMENTS]; int CableThetaVelocity[NUMBER_OF_CABLE_SEGMENTS]; int CablePhiVelocity[NUMBER_OF_CABLE_SEGMENTS]; VECTORCH CableForce[NUMBER_OF_CABLE_SEGMENTS]; VECTORCH CableDirection[NUMBER_OF_CABLE_SEGMENTS]; VECTORCH CableThetaDirection[NUMBER_OF_CABLE_SEGMENTS]; VECTORCH CablePhiDirection[NUMBER_OF_CABLE_SEGMENTS]; extern void MakeMatrixFromDirection(VECTORCH *directionPtr, MATRIXCH *matrixPtr); void D3D_DrawCable(VECTORCH *centrePtr, MATRIXCH *orientationPtr) { { // Turn OFF texturing if it is on... if (CurrTextureHandle != NULL) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, NULL, ExecBufInstPtr); CurrTextureHandle = NULL; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); if (NumVertices) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, FALSE, ExecBufInstPtr); } MeshXScale = 4096/16; MeshZScale = 4096/16; for (int field=0; field<3; field++) { int i=0; int x; for (x=(0+field*15); x<(16+field*15); x++) { int z; for(z=0; z<16; z++) { VECTORCH *point = &MeshVertex[i]; { int innerRadius = 20; VECTORCH radius; int theta = ((4096*z)/15)&4095; int rOffset = GetSin((x*64+theta/32-CloakingPhase)&4095); rOffset = MUL_FIXED(rOffset,rOffset)/512; radius.vx = MUL_FIXED(innerRadius+rOffset/8,GetSin(theta)); radius.vy = MUL_FIXED(innerRadius+rOffset/8,GetCos(theta)); radius.vz = 0; RotateVector(&radius,orientationPtr); point->vx = centrePtr[x].vx+radius.vx; point->vy = centrePtr[x].vy+radius.vy; point->vz = centrePtr[x].vz+radius.vz; MeshVertexColour[i] = RGBALIGHT_MAKE(0,rOffset,255,128); } TranslatePointIntoViewspace(point); /* is particle within normal view frustrum ? */ if(AvP.PlayerType==I_Alien) /* wide frustrum */ { if(( (-point->vx <= point->vz*2) &&(point->vx <= point->vz*2) &&(-point->vy <= point->vz*2) &&(point->vy <= point->vz*2) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } else { if(( (-point->vx <= point->vz) &&(point->vx <= point->vz) &&(-point->vy <= point->vz) &&(point->vy <= point->vz) )) { MeshVertexOutcode[i]=1; } else { MeshVertexOutcode[i]=0; } } i++; } } //textprint("\n"); if ((MeshVertexOutcode[0]&&MeshVertexOutcode[15]&&MeshVertexOutcode[240]&&MeshVertexOutcode[255])) { D3D_DrawMoltenMetalMesh_Unclipped(); // D3D_DrawWaterMesh_Unclipped(); } else // else if (MeshVertexOutcode[0]||MeshVertexOutcode[15]||MeshVertexOutcode[240]||MeshVertexOutcode[255]) { D3D_DrawMoltenMetalMesh_Clipped(); // D3D_DrawWaterMesh_Clipped(); } } OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_ZWRITEENABLE, TRUE, ExecBufInstPtr); } void SetupFMVTexture(FMVTEXTURE *ftPtr) { DDSURFACEDESC ddsd; memcpy(&ddsd, &(d3d.TextureFormat[d3d.CurrentTextureFormat].ddsd), sizeof(ddsd)); ddsd.dwSize = sizeof(ddsd); ddsd.dwFlags = (DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT); ddsd.ddsCaps.dwCaps = (DDSCAPS_SYSTEMMEMORY|DDSCAPS_TEXTURE); ddsd.dwHeight = FMV_SIZE; ddsd.dwWidth = FMV_SIZE; LastError = lpDD->CreateSurface(&ddsd, &(ftPtr->SrcSurface), NULL); LOGDXERR(LastError); DDBLTFX ddbltfx; memset(&ddbltfx, 0, sizeof(ddbltfx)); ddbltfx.dwSize = sizeof(ddbltfx); ddbltfx.dwFillColor = 0;// (2<<11)+(26<<5)+8; LastError=(ftPtr->SrcSurface)->Blt(NULL, NULL, NULL, DDBLT_COLORFILL | DDBLT_WAIT, &ddbltfx); LOGDXERR(LastError); LastError = (ftPtr->SrcSurface)->QueryInterface(IID_IDirect3DTexture, (LPVOID*) &(ftPtr->SrcTexture)); LOGDXERR(LastError); { int PalCaps; if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { PalCaps = (DDPCAPS_8BIT | DDPCAPS_ALLOW256); } else if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED4) { PalCaps = DDPCAPS_4BIT; } else { PalCaps = 0; } if (PalCaps) { LPDIRECTDRAWPALETTE destPalette = NULL; LastError = lpDD->CreatePalette(PalCaps, ftPtr->SrcPalette, &destPalette, NULL); LOGDXERR(LastError); LastError = (ftPtr->SrcSurface)->SetPalette(destPalette); // LastError = tempSurface->SetPalette(destPalette); LOGDXERR(LastError); } } ftPtr->DestTexture = 0; ftPtr->SoundVolume = 0; } void UpdateFMVTexture(FMVTEXTURE *ftPtr) { LPDIRECTDRAWSURFACE destSurface = NULL; LOCALASSERT(ftPtr); LOCALASSERT(ftPtr->ImagePtr); LPDIRECTDRAWSURFACE srcSurface = ftPtr->SrcSurface; LPDIRECT3DTEXTURE srcTexture = ftPtr->SrcTexture; LOCALASSERT(srcSurface); DDSURFACEDESC ddsd; memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = srcSurface->Lock(NULL,&ddsd,DDLOCK_WAIT,NULL); // check for success { if (!NextFMVTextureFrame(ftPtr,(void*)ddsd.lpSurface)) { LastError = srcSurface->Unlock(NULL); LOGDXERR(LastError); return; } } LastError = srcSurface->Unlock(NULL); LOGDXERR(LastError); if (ftPtr->DestTexture) { ReleaseD3DTexture(ftPtr->DestTexture); ftPtr->DestTexture = 0; } // Query destination surface for a texture interface. memset(&ddsd, 0, sizeof(DDSURFACEDESC)); ddsd.dwSize = sizeof(DDSURFACEDESC); LastError = srcSurface->GetSurfaceDesc(&ddsd); LOGDXERR(LastError); ddsd.dwFlags = (DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT); ddsd.ddsCaps.dwCaps = (DDSCAPS_TEXTURE | DDSCAPS_ALLOCONLOAD ); LastError = lpDD->CreateSurface(&ddsd, &destSurface, NULL); LOGDXERR(LastError); { int PalCaps; if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { PalCaps = (DDPCAPS_8BIT | DDPCAPS_ALLOW256); } else if (ddsd.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED4) { PalCaps = DDPCAPS_4BIT; } else { PalCaps = 0; } #if 1 if (PalCaps) { LPDIRECTDRAWPALETTE destPalette = NULL; LastError = lpDD->CreatePalette(PalCaps, ftPtr->SrcPalette, &destPalette, NULL); LOGDXERR(LastError); UpdateFMVTexturePalette(ftPtr); LastError = destSurface->SetPalette(destPalette); LOGDXERR(LastError); LastError = srcSurface->SetPalette(destPalette); LOGDXERR(LastError); destPalette->Release(); } #endif } LastError = destSurface->QueryInterface(IID_IDirect3DTexture,(LPVOID*) &(ftPtr->DestTexture)); LOGDXERR(LastError); LastError = (ftPtr->DestTexture)->Load(srcTexture); LOGDXERR(LastError); LastError = (ftPtr->DestTexture)->GetHandle(d3d.lpD3DDevice, &(ftPtr->ImagePtr->D3DHandle)); LOGDXERR(LastError); // ftPtr->ImagePtr->DDSurface = destSurface; // ftPtr->ImagePtr->D3DTexture = (ftPtr->DestTexture); if (destSurface) ReleaseDDSurface(destSurface); } #if 0 static int GammaSetting; void UpdateGammaSettings(int g, int forceUpdate) { LPDIRECTDRAWGAMMACONTROL handle; DDGAMMARAMP gammaValues; if (g==GammaSetting && !forceUpdate) return; lpDDSPrimary->QueryInterface(IID_IDirectDrawGammaControl,(LPVOID*)&handle); // handle->GetGammaRamp(0,&gammaValues); for (int i=0; i<=255; i++) { int u = ((i*65536)/255); int m = MUL_FIXED(u,u); int l = MUL_FIXED(2*u,ONE_FIXED-u); int a; a = m/256+MUL_FIXED(g,l); if (a<0) a=0; if (a>255) a=255; gammaValues.red[i]=a*256; gammaValues.green[i]=a*256; gammaValues.blue[i]=a*256; } // handle->SetGammaRamp(0,&gammaValues); handle->SetGammaRamp(DDSGR_CALIBRATE,&gammaValues); GammaSetting=g; // handle->SetGammaRamp(DDSGR_CALIBRATE,&gammaValues); //handle->GetGammaRamp(0,&gammaValues); RELEASE(handle); } #endif // For extern "C" }; #if 0 void D3D_Polygon_Output(RENDERVERTEX *renderVerticesPtr) { D3DTEXTUREHANDLE TextureHandle; float ZNear; float RecipW, RecipH; if(RenderPolygon.IsTextured) { int texoffset = RenderPolygon.ImageIndex; TextureHandle = (D3DTEXTUREHANDLE) ImageHeaderArray[texoffset].D3DHandle; if(ImageHeaderArray[texoffset].ImageWidth==128) { RecipW = 1.0 /128.0; } else { float width = (float) ImageHeaderArray[texoffset].ImageWidth; RecipW = (1.0 / width); } if(ImageHeaderArray[texoffset].ImageHeight==128) { RecipH = 1.0 / 128.0; } else { float height = (float) ImageHeaderArray[texoffset].ImageHeight; RecipH = (1.0 / height); } } /* OUTPUT VERTICES TO EXECUTE BUFFER */ { int i = RenderPolygon.NumberOfVertices; RENDERVERTEX *vertices = renderVerticesPtr; do { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; float oneOverZ; oneOverZ = (1.0)/vertices->Z; float zvalue; { int x = (vertices->X*(Global_VDB_Ptr->VDB_ProjX+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreX; if (xVDB_ClipLeft) { x=Global_VDB_Ptr->VDB_ClipLeft; } else if (x>Global_VDB_Ptr->VDB_ClipRight) { x=Global_VDB_Ptr->VDB_ClipRight; } vertexPtr->sx=x; } { int y = (vertices->Y*(Global_VDB_Ptr->VDB_ProjY+1))/vertices->Z+Global_VDB_Ptr->VDB_CentreY; if (yVDB_ClipUp) { y=Global_VDB_Ptr->VDB_ClipUp; } else if (y>Global_VDB_Ptr->VDB_ClipDown) { y=Global_VDB_Ptr->VDB_ClipDown; } vertexPtr->sy=y; } if (RenderPolygon.IsTextured) { vertexPtr->tu = ((float)(vertices->U>>16)+0.5) * RecipW; vertexPtr->tv = ((float)(vertices->V>>16)+0.5) * RecipH; vertexPtr->rhw = oneOverZ; } { zvalue = vertices->Z+HeadUpDisplayZOffset; // zvalue /= 65536.0; zvalue = ((zvalue-ZNear)/zvalue); } if (RenderPolygon.TranslucencyMode!=TRANSLUCENCY_OFF) { vertexPtr->color = RGBALIGHT_MAKE(vertices->R,vertices->G,vertices->B, vertices->A); } else { vertexPtr->color = RGBLIGHT_MAKE(vertices->R,vertices->G,vertices->B); } if (RenderPolygon.IsSpecularLit) { vertexPtr->specular = RGBALIGHT_MAKE(vertices->R/2,vertices->G/2,vertices->B/2, 0); } else { vertexPtr->specular=0; } vertexPtr->sz = zvalue; #if FOG_ON if(CurrentRenderStates.FogIsOn) { if (vertices->Z>CurrentRenderStates.FogDistance) { int fog = ((vertices->Z-CurrentRenderStates.FogDistance)/FOG_SCALE); if (fog<0) fog=0; if (fog>254) fog=254; fog=255-fog; vertexPtr->specular|=RGBALIGHT_MAKE(0,0,0,fog); } else { vertexPtr->specular|=RGBALIGHT_MAKE(0,0,0,255); } } #endif vertices++; NumVertices++; } while(--i); } CheckTranslucencyModeIsCorrect(RenderPolygon.TranslucencyMode); if (D3DTexturePerspective != Yes) { D3DTexturePerspective = Yes; OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREPERSPECTIVE, TRUE, ExecBufInstPtr); } if (TextureHandle != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, TextureHandle, ExecBufInstPtr); CurrTextureHandle = TextureHandle; } D3D_OutputTriangles(); } #endif void r2rect :: AlphaFill ( unsigned char R, unsigned char G, unsigned char B, unsigned char translucency ) const { GLOBALASSERT ( bValidPhys() ); if (y1<=y0) return; #if 1 /* OUTPUT quadVerticesPtr TO EXECUTE BUFFER */ { D3DCOLOR Colour; Colour = RGBALIGHT_MAKE(R,G,B,translucency); { D3DTLVERTEX *vertexPtr = &((LPD3DTLVERTEX)ExecuteBufferDataArea)[NumVertices]; /* Vertex 0 = Top left */ vertexPtr->sx= x0; vertexPtr->sy= y0; vertexPtr->color = Colour; NumVertices++; vertexPtr++; /* Vertex 1 = Top right */ vertexPtr->sx=( x1 - 1); vertexPtr->sy=( y0 ); vertexPtr->color = Colour; NumVertices++; vertexPtr++; /* Vertex 2 = Bottom right */ vertexPtr->sx=( x1 - 1); vertexPtr->sy=( y1 - 1); vertexPtr->color = Colour; NumVertices++; vertexPtr++; /* Vertex 3 = Bottom left */ vertexPtr->sx=x0; vertexPtr->sy=( y1 - 1); vertexPtr->color = Colour; NumVertices++; } } // set correct texture handle if (0 != CurrTextureHandle) { OP_STATE_RENDER(1, ExecBufInstPtr); STATE_DATA(D3DRENDERSTATE_TEXTUREHANDLE, 0, ExecBufInstPtr); CurrTextureHandle = 0; } CheckTranslucencyModeIsCorrect(TRANSLUCENCY_GLOWING); /* output triangles to execute buffer */ OP_TRIANGLE_LIST(2, ExecBufInstPtr); OUTPUT_TRIANGLE(0,1,3, 4); OUTPUT_TRIANGLE(1,2,3, 4); /* check to see if buffer is getting full */ if (NumVertices > (MaxVerticesInExecuteBuffer-12)) { WriteEndCodeToExecuteBuffer(); UnlockExecuteBufferAndPrepareForUse(); ExecuteBuffer(); LockExecuteBuffer(); } #endif } extern void D3D_RenderHUDNumber_Centred(unsigned int number,int x,int y,int colour); extern void D3D_RenderHUDString(char *stringPtr,int x,int y,int colour); extern void D3D_RenderHUDString_Clipped(char *stringPtr,int x,int y,int colour); extern void D3D_RenderHUDString_Centred(char *stringPtr, int centreX, int y, int colour); extern void D3D_RenderHUDNumber_Centred(unsigned int number,int x,int y,int colour) { struct VertexTag quadVertices[4]; int noOfDigits=3; int h = MUL_FIXED(HUDScaleFactor,HUD_DIGITAL_NUMBERS_HEIGHT); int w = MUL_FIXED(HUDScaleFactor,HUD_DIGITAL_NUMBERS_WIDTH); quadVertices[0].Y = y; quadVertices[1].Y = y; quadVertices[2].Y = y + h; quadVertices[3].Y = y + h; x += (3*w)/2; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); do { int digit = number%10; number/=10; { int topLeftU; int topLeftV; if (digit<8) { topLeftU = 1+(digit)*16; topLeftV = 1; } else { topLeftU = 1+(digit-8)*16; topLeftV = 1+24; } if (AvP.PlayerType == I_Marine) topLeftV+=80; quadVertices[0].U = topLeftU; quadVertices[0].V = topLeftV; quadVertices[1].U = topLeftU + HUD_DIGITAL_NUMBERS_WIDTH; quadVertices[1].V = topLeftV; quadVertices[2].U = topLeftU + HUD_DIGITAL_NUMBERS_WIDTH; quadVertices[2].V = topLeftV + HUD_DIGITAL_NUMBERS_HEIGHT; quadVertices[3].U = topLeftU; quadVertices[3].V = topLeftV + HUD_DIGITAL_NUMBERS_HEIGHT; x -= 1+w; quadVertices[0].X = x; quadVertices[3].X = x; quadVertices[1].X = x + w; quadVertices[2].X = x + w; D3D_HUDQuad_Output ( HUDFontsImageNumber, quadVertices, colour ); } } while(--noOfDigits); } extern void D3D_RenderHUDString(char *stringPtr,int x,int y,int colour) { struct VertexTag quadVertices[4]; quadVertices[0].Y = y-1; quadVertices[1].Y = y-1; quadVertices[2].Y = y + HUD_FONT_HEIGHT + 1; quadVertices[3].Y = y + HUD_FONT_HEIGHT + 1; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); while( *stringPtr ) { char c = *stringPtr++; { int topLeftU = 1+((c-32)&15)*16; int topLeftV = 1+((c-32)>>4)*16; quadVertices[0].U = topLeftU - 1; quadVertices[0].V = topLeftV - 1; quadVertices[1].U = topLeftU + HUD_FONT_WIDTH + 1; quadVertices[1].V = topLeftV - 1; quadVertices[2].U = topLeftU + HUD_FONT_WIDTH + 1; quadVertices[2].V = topLeftV + HUD_FONT_HEIGHT + 1; quadVertices[3].U = topLeftU - 1; quadVertices[3].V = topLeftV + HUD_FONT_HEIGHT + 1; quadVertices[0].X = x - 1; quadVertices[3].X = x - 1; quadVertices[1].X = x + HUD_FONT_WIDTH + 1; quadVertices[2].X = x + HUD_FONT_WIDTH + 1; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } x += AAFontWidths[c]; } } extern void D3D_RenderHUDString_Clipped(char *stringPtr,int x,int y,int colour) { struct VertexTag quadVertices[4]; LOCALASSERT(y<=0); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); quadVertices[2].Y = y + HUD_FONT_HEIGHT + 1; quadVertices[3].Y = y + HUD_FONT_HEIGHT + 1; quadVertices[0].Y = 0; quadVertices[1].Y = 0; while ( *stringPtr ) { char c = *stringPtr++; { int topLeftU = 1+((c-32)&15)*16; int topLeftV = 1+((c-32)>>4)*16; quadVertices[0].U = topLeftU - 1; quadVertices[0].V = topLeftV - y; quadVertices[1].U = topLeftU + HUD_FONT_WIDTH+1; quadVertices[1].V = topLeftV - y; quadVertices[2].U = topLeftU + HUD_FONT_WIDTH+1; quadVertices[2].V = topLeftV + HUD_FONT_HEIGHT+1; quadVertices[3].U = topLeftU - 1; quadVertices[3].V = topLeftV + HUD_FONT_HEIGHT+1; quadVertices[0].X = x - 1; quadVertices[3].X = x - 1; quadVertices[1].X = x + HUD_FONT_WIDTH + 1; quadVertices[2].X = x + HUD_FONT_WIDTH + 1; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } x += AAFontWidths[c]; } } void D3D_RenderHUDString_Centred(char *stringPtr, int centreX, int y, int colour) { int length = 0; char *ptr = stringPtr; while(*ptr) { length+=AAFontWidths[*ptr++]; } length = MUL_FIXED(HUDScaleFactor,length); // D3D_RenderHUDString(stringPtr,centreX-length/2,y,colour); int x = centreX-length/2; { struct VertexTag quadVertices[4]; quadVertices[0].Y = y-MUL_FIXED(HUDScaleFactor,1); quadVertices[1].Y = y-MUL_FIXED(HUDScaleFactor,1); quadVertices[2].Y = y + MUL_FIXED(HUDScaleFactor,HUD_FONT_HEIGHT + 1); quadVertices[3].Y = y + MUL_FIXED(HUDScaleFactor,HUD_FONT_HEIGHT + 1); CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); while( *stringPtr ) { char c = *stringPtr++; { int topLeftU = 1+((c-32)&15)*16; int topLeftV = 1+((c-32)>>4)*16; #if 1 quadVertices[0].U = topLeftU - 1; quadVertices[0].V = topLeftV - 1; quadVertices[1].U = topLeftU + HUD_FONT_WIDTH + 1; quadVertices[1].V = topLeftV - 1; quadVertices[2].U = topLeftU + HUD_FONT_WIDTH + 1; quadVertices[2].V = topLeftV + HUD_FONT_HEIGHT + 1; quadVertices[3].U = topLeftU - 1; quadVertices[3].V = topLeftV + HUD_FONT_HEIGHT + 1; #else quadVertices[0].U = topLeftU ; quadVertices[0].V = topLeftV ; quadVertices[1].U = topLeftU + HUD_FONT_WIDTH ; quadVertices[1].V = topLeftV ; quadVertices[2].U = topLeftU + HUD_FONT_WIDTH ; quadVertices[2].V = topLeftV + HUD_FONT_HEIGHT ; quadVertices[3].U = topLeftU ; quadVertices[3].V = topLeftV + HUD_FONT_HEIGHT ; #endif quadVertices[0].X = x - MUL_FIXED(HUDScaleFactor,1); quadVertices[3].X = x - MUL_FIXED(HUDScaleFactor,1); quadVertices[1].X = x + MUL_FIXED(HUDScaleFactor,HUD_FONT_WIDTH + 1); quadVertices[2].X = x + MUL_FIXED(HUDScaleFactor,HUD_FONT_WIDTH + 1); D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } x += MUL_FIXED(HUDScaleFactor,AAFontWidths[c]); } } } extern "C" { extern void RenderString(char *stringPtr, int x, int y, int colour) { D3D_RenderHUDString(stringPtr,x,y,colour); } extern void RenderStringCentred(char *stringPtr, int centreX, int y, int colour) { int length = 0; char *ptr = stringPtr; while(*ptr) { length+=AAFontWidths[*ptr++]; } D3D_RenderHUDString(stringPtr,centreX-length/2,y,colour); } extern void RenderStringVertically(char *stringPtr, int centreX, int bottomY, int colour) { struct VertexTag quadVertices[4]; int y = bottomY; quadVertices[0].X = centreX - (HUD_FONT_HEIGHT/2) - 1; quadVertices[1].X = quadVertices[0].X; quadVertices[2].X = quadVertices[0].X+2+HUD_FONT_HEIGHT*1; quadVertices[3].X = quadVertices[2].X; CheckFilteringModeIsCorrect(FILTERING_BILINEAR_OFF); while( *stringPtr ) { char c = *stringPtr++; { int topLeftU = 1+((c-32)&15)*16; int topLeftV = 1+((c-32)>>4)*16; quadVertices[0].U = topLeftU - 1; quadVertices[0].V = topLeftV - 1; quadVertices[1].U = topLeftU + HUD_FONT_WIDTH; quadVertices[1].V = topLeftV - 1; quadVertices[2].U = topLeftU + HUD_FONT_WIDTH; quadVertices[2].V = topLeftV + HUD_FONT_HEIGHT + 1; quadVertices[3].U = topLeftU - 1; quadVertices[3].V = topLeftV + HUD_FONT_HEIGHT + 1; quadVertices[0].Y = y ; quadVertices[1].Y = y - HUD_FONT_WIDTH*1 -1; quadVertices[2].Y = y - HUD_FONT_WIDTH*1 -1; quadVertices[3].Y = y ; D3D_HUDQuad_Output ( AAFontImageNumber, quadVertices, colour ); } y -= AAFontWidths[c]; } } };