int RunRenderThreads (int nTask, int nThreads)
{
#if USE_OPENMP

    return 0;

#else

#	if DBG
    time_t	t0 = 0, t2 = 0;
    int		nActive;
    static	int nLockups = 0;
#	endif
    int		i;

    if (!gameStates.app.bMultiThreaded)
        return 0;
    tiRender.nTask = (tRenderTask) nTask;
    if (nThreads < 0)
        nThreads = gameStates.app.nThreads;
    for (i = 0; i < nThreads; i++)
        tiRender.ti [i].bExec = 1;
#if DBG
    t0 = clock ();
    while ((nActive = ThreadsActive (nThreads)) && (clock () - t0 < 1000)) {
        G3_SLEEP (0);
        if (nActive < nThreads) {
            if (!t2)
                t2 = clock ();
            else if (clock () - t2 > 33) {	//slower threads must not take more than 33 ms over the fastest one
                PrintLog ("threads locked up (task: %d)\n", nTask);
                for (i = 0; i < nThreads; i++)
                    tiRender.ti [i].bExec = 0;
                if (++nLockups > 100) {
                    gameStates.app.bMultiThreaded = 0;
                    gameStates.app.nThreads = 1;
                }
            }
        }
    }
#	else
    while (ThreadsActive (nThreads))
        G3_SLEEP (0);
#	endif
    return 1;

#endif
}
Beispiel #2
0
void hmp_stop(hmp_file *hmp) 
{
	MIDIHDR *mhdr;
	if (!hmp->stop) {
		hmp->stop = 1;
		//PumpMessages();
		midiStreamStop(hmp->hmidi);
      while (hmp->bufs_in_mm)
         {
			//PumpMessages();
			G3_SLEEP(0);
         }
	}
	while ((mhdr = hmp->evbuf)) {
		midiOutUnprepareHeader((HMIDIOUT)hmp->hmidi, mhdr, sizeof(MIDIHDR));
		hmp->evbuf = mhdr->lpNext;
		delete[] mhdr;
		mhdr = NULL;
	}

	if (hmp->hmidi) {
		midiStreamClose(hmp->hmidi);
		hmp->hmidi = NULL;
	}
}
Beispiel #3
0
int _CDECL_ SoundThread (void *pThreadId)
{
do {
	while (!tiSound.ti.bExec) {
		G3_SLEEP (1);
		if (tiSound.ti.bDone)
			return 0;
		}
	if (tiSound.nTask == stOpenAudio) {
		DigiInit (tiSound.fSlowDown);
		}
	else if (tiSound.nTask == stCloseAudio) {
		DigiExit ();
		}
	else if (tiSound.nTask == stReconfigureAudio) {
		FreeAddonSounds ();
		DigiExit ();
		DigiInit (tiSound.fSlowDown);
		if (tiSound.fSlowDown == 1.0f) {
			gameData.songs.tPos = gameData.songs.tSlowDown - gameData.songs.tStart + 
										 2 * (SDL_GetTicks () - gameData.songs.tSlowDown) / gameOpts->gameplay.nSlowMotionSpeedup;
			}
		else {
			gameData.songs.tSlowDown = SDL_GetTicks ();
			gameData.songs.tPos = gameData.songs.tSlowDown - gameData.songs.tStart;
			}
		PlayLevelSong (gameData.missions.nCurrentLevel, 1);
		}
	tiSound.ti.bExec = 0;
	} while (!tiSound.ti.bDone);
return 0;
}
void EndEffectsThread (void)
{
    if (!tiEffects.pThread)
        return;
    tiEffects.bDone = 1;
    while (tiEffects.bDone)
        G3_SLEEP (0);
    tiEffects.pThread = NULL;
}
Beispiel #5
0
void EndSoundThread (void)
{
if (tiSound.ti.pThread) {
	WaitForSoundThread ();
	tiSound.ti.bDone = 1;
	G3_SLEEP (100);
	//SDL_KillThread (tiSound.ti.pThread);
	tiSound.ti.pThread = NULL;
	}	
}
bool WaitForRenderThreads (void)
{
#if !USE_OPENMP
    if (gameStates.app.bMultiThreaded) {
        while (tiRender.ti [0].bExec || tiRender.ti [1].bExec)
            G3_SLEEP (0);	//already running, so wait
        return true;
    }
#endif
    return false;
}
bool WaitForEffectsThread (void)
{
#if !USE_OPENMP
    if ((gameStates.app.bMultiThreaded > 1) && tiEffects.pThread) {
        while (tiEffects.bExec)
            G3_SLEEP (0);
        return true;
    }
#endif
    return false;
}
void EndTranspRenderThread (void)
{
#if TRANSPRENDER_THREADS
    tiTranspRender.ti [0].bDone =
        tiTranspRender.ti [1].bDone = 1;
    G3_SLEEP (10);
    for (int i = 0; i < 2; i++) {
        if (tiTranspRender.ti [i].pThread) {
            //SDL_KillThread (tiTranspRender.ti [0].pThread);
            tiTranspRender.ti [i].pThread = NULL;
        }
    }
#endif
}
Beispiel #9
0
void DonationNotification (void)
{
if (gameConfig.nTotalTime > (25 * 60)) {	// played for more than 25 hours
	SetScreenMode (SCREEN_MENU);
	int nFade = gameOpts->menus.nFade;
	gameOpts->menus.nFade = 250;
	messageBox.Show (TXT_PLEASE_DONATE);
	G3_SLEEP (10000);
	gameOpts->menus.nFade = 500;
	messageBox.Clear ();
	gameOpts->menus.nFade = nFade;
	gameConfig.nTotalTime = 0;	// only display after another 25 hours
	}
}
Beispiel #10
0
float CoronaVisibility (int nQuery)
{
	GLuint	nSamples = 0;
	GLint		bAvailable = 0;
	int		nAttempts = 2;
	float		fIntensity;
#if DBG
	GLint		nError;
#endif

if (! (ogl.m_states.bOcclusionQuery && nQuery) || (CoronaStyle () != 1))
	return 1;
if (! (gameStates.render.bQueryCoronas || gameData.render.lights.coronaSamples [nQuery - 1]))
	return 0;
for (;;) {
	glGetQueryObjectiv (gameData.render.lights.coronaQueries [nQuery - 1], GL_QUERY_RESULT_AVAILABLE_ARB, &bAvailable);
	if (glGetError ()) {
#if DBG
		glGetQueryObjectiv (gameData.render.lights.coronaQueries [nQuery - 1], GL_QUERY_RESULT_AVAILABLE_ARB, &bAvailable);
		if ((nError = glGetError ()))
#endif
			return 0;
		}
	if (bAvailable)
		break;
	if (!--nAttempts)
		return 0;
	G3_SLEEP (1);
	};
glGetQueryObjectuiv (gameData.render.lights.coronaQueries [nQuery - 1], GL_QUERY_RESULT_ARB, &nSamples);
if (glGetError ())
	return 0;
if (gameStates.render.bQueryCoronas == 1) {
#if DBG
	if (!nSamples) {
		GLint nBits;
		glGetQueryiv (GL_SAMPLES_PASSED, GL_QUERY_COUNTER_BITS, &nBits);
		glGetQueryObjectuiv (gameData.render.lights.coronaQueries [nQuery - 1], GL_QUERY_RESULT_ARB, &nSamples);
		}
#endif
	return (float) (gameData.render.lights.coronaSamples [nQuery - 1] = nSamples);
	}
fIntensity = (float) nSamples / (float) gameData.render.lights.coronaSamples [nQuery - 1];
#if DBG
if (fIntensity > 1)
	fIntensity = 1;
#endif
return (fIntensity > 1) ? 1 : (float) sqrt (fIntensity);
}
Beispiel #11
0
int RunEmitterThread (tParticleEmitter *emitterP, int nCurTime, tRenderTask nTask)
{
int	i;

if (!gameStates.app.bMultiThreaded)
	return 0;
while (tiRender.ti [0].bExec && tiRender.ti [1].bExec)
	G3_SLEEP (0);
i = tiRender.ti [0].bExec ? 1 : 0;
tiRender.emitters [i] = emitterP;
tiRender.nCurTime [i] = nCurTime;
tiRender.nTask = nTask;
tiRender.ti [i].bExec = 1;
return 1;
}
int _CDECL_ EffectsThread (void *pThreadId)
{
    do {
        while (!tiEffects.bExec) {
            G3_SLEEP (0);
            if (tiEffects.bDone) {
                tiEffects.bDone = 0;
                return 0;
            }
        }
        DoParticleFrame ();
        lightningManager.DoFrame ();
        sparkManager.DoFrame ();
        tiEffects.bExec = 0;
    } while (!tiEffects.bDone);
    tiEffects.bDone = 0;
    return 0;
}
Beispiel #13
0
void StartSoundThread (void)
{
#if 1
if (!tiSound.ti.pThread) {
#else
if (gameData.app.bUseMultiThreading [rtSound] && !tiSound.ti.pThread) {
#endif
	memset (&tiSound, 0, sizeof (tiSound));
	tiSound.ti.nId = 0;
	tiSound.ti.pThread = SDL_CreateThread (SoundThread, &tiSound.ti.nId);
	}
}

//------------------------------------------------------------------------------

void EndSoundThread (void)
{
if (tiSound.ti.pThread) {
	WaitForSoundThread ();
	tiSound.ti.bDone = 1;
	do {
		G3_SLEEP (1);
		} while (tiSound.ti.bDone);
	//SDL_KillThread (tiSound.ti.pThread);
	tiSound.ti.pThread = NULL;
	}	
}

//------------------------------------------------------------------------------

void ControlSoundThread (void)
{
#if 1
StartSoundThread ();
#else
if (gameStates.app.bMultiThreaded) {
	if (gameData.app.bUseMultiThreading [rtSound])
		StartSoundThread ();
	else
		EndSoundThread ();
	}
#endif
}
void EndRenderThreads (void)
{
    if (!gameStates.app.bMultiThreaded)
        return;
#if !USE_OPENMP
    for (int i = 0; i < gameStates.app.nThreads; i++)
        tiRender.ti [i].bDone = 1;
    G3_SLEEP (10);
    for (int i = 0; i < gameStates.app.nThreads; i++) {
        if (tiRender.ti [i].pThread) {
            //SDL_KillThread (tiRender.ti [0].pThread);
            tiRender.ti [i].pThread = NULL;
        }
    }
    SDL_DestroyMutex (tiRender.semaphore);
    tiRender.semaphore = NULL;
    EndTranspRenderThread ();
#endif
    EndEffectsThread ();
}
int _CDECL_ TranspRenderThread (void *pThreadId)
{
#if TRANSPRENDER_THREADS
    do {
        while (!(tiTranspRender.ti [0].bExec || tiTranspRender.ti [1].bExec))
            G3_SLEEP (0);
        for (int i = 0; i < 2; i++) {
            if (tiTranspRender.ti [i].bExec) {
                transparencyRenderer.Add ((tTranspItemType) tiTranspRender.itemData [i].nType,
                                          &tiTranspRender.itemData [i].item,
                                          tiTranspRender.itemData [i].nSize,
                                          tiTranspRender.itemData [i].nDepth,
                                          tiTranspRender.itemData [i].nIndex);
                tiTranspRender.ti [i].bExec = 0;
            }
        }
    } while (!(tiTranspRender.ti [0].bDone && tiTranspRender.ti [1].bDone));
#endif
    return 0;
}
Beispiel #16
0
void BadHardwareNotification (void)
{
#if 1//!DBG
if (!ogl.m_states.bShadersOk && (gameConfig.nVersion != D2X_IVER)) {
	SetScreenMode (SCREEN_MENU);
	int nFade = gameOpts->menus.nFade;
	gameOpts->menus.nFade = 250;
#if 1
	for (int i = 0; i < 2; i++) {	// make the message flash a few times
		messageBox.Show (TXT_BAD_HARDWARE);
		messageBox.Clear ();
		}
#endif
	messageBox.Show (TXT_BAD_HARDWARE);
	G3_SLEEP (4000);
	gameOpts->menus.nFade = 500;
	messageBox.Clear ();
	gameOpts->menus.nFade = nFade;
	gameConfig.nVersion = D2X_IVER;
	}
#endif
}
Beispiel #17
0
int CTransparencyRenderer::AddMT (tTranspItemType nType, void *itemData, int itemSize, int nDepth, int nIndex, int nThread)
{
if (!gameStates.app.bMultiThreaded || (nThread < 0) || !gameData.app.bUseMultiThreading [rtTranspRender])
	return Add (nType, itemData, itemSize, nDepth, nIndex);
#if UNIFY_THREADS
WaitForRenderThreads ();
#else
while (tiTranspRender.ti [nThread].bExec)
	G3_SLEEP (0);
#endif
tiTranspRender.itemData [nThread].nType = nType;
tiTranspRender.itemData [nThread].nSize = itemSize;
tiTranspRender.itemData [nThread].nDepth = nDepth;
tiTranspRender.itemData [nThread].nIndex = nIndex;
memcpy (&tiTranspRender.itemData [nThread].item, itemData, itemSize);
#if UNIFY_THREADS
RunRenderThreads (rtTranspRender, 2);
#else
tiTranspRender.ti [nThread].bExec = 1;
#endif
return 1;
}
Beispiel #18
0
int KeyInKeyTime (fix * time)
{
    int key = 0;
    int bLegacy = gameOpts->legacy.bInput;

    gameOpts->legacy.bInput = 1;

    if (!bInstalled)
        KeyInit ();
    event_poll (SDL_KEYDOWNMASK | SDL_KEYUPMASK);
    if (keyData.nKeyTail != keyData.nKeyHead) {
        key = keyData.keyBuffer [keyData.nKeyHead];
        if (key == KEY_CTRLED + KEY_ALTED + KEY_ENTER)
            exit (0);
        keyData.nKeyHead = KeyAddKey(keyData.nKeyHead);
        if (time)
            *time = keyData.xTimePressed [keyData.nKeyHead];
    }
    else if (!time)
        G3_SLEEP (0);
    gameOpts->legacy.bInput = bLegacy;
    return key;
}
Beispiel #19
0
int _CDECL_ SoundThread (void *pThreadId)
{
do {
	while (!tiSound.ti.bExec) {
		G3_SLEEP (1);
		if (tiSound.ti.bDone) {
			tiSound.ti.bDone = 0;
			return 0;
			}
		}
	if (tiSound.nTask == stOpenAudio) {
		audio.Setup (tiSound.fSlowDown);
		}
	else if (tiSound.nTask == stCloseAudio) {
		audio.Shutdown ();
		}
	else if (tiSound.nTask == stReconfigureAudio) {
		FreeAddonSounds ();
		audio.Shutdown ();
		audio.Setup (tiSound.fSlowDown);
		if (tiSound.fSlowDown == 1.0f) {
			songManager.SetPos (songManager.SlowDown () - songManager.Start () + 
									  2 * (SDL_GetTicks () - songManager.SlowDown ()) / gameOpts->gameplay.nSlowMotionSpeedup);
			songManager.SetSlowDown (0);
			}
		else {
			songManager.SetSlowDown (SDL_GetTicks ());
			songManager.SetPos (songManager.SlowDown () - songManager.Start ());
			}
		songManager.PlayLevelSong (gameData.missions.nCurrentLevel, 1, false);
		}
	tiSound.ti.bExec = 0;
	} while (!tiSound.ti.bDone);
tiSound.ti.bDone = 0;
return 0;
}
Beispiel #20
0
int PiggyBitmapPageIn (int bmi, int bD1, bool bHires)
{
	CBitmap*	bmP, * bmoP;
	int		i, bmiSave;

	//bD1 = gameStates.app.bD1Mission;
bmiSave = 0;
#if 0
Assert (bmi >= 0);
Assert (bmi < MAX_BITMAP_FILES);
Assert (bmi < gameData.pig.tex.nBitmaps [bD1]);
Assert (bitmapCacheSize > 0);
#endif
if (bmi < 1)
	return 0;
if (bmi >= MAX_BITMAP_FILES)
	return 0;
if (bmi >= gameData.pig.tex.nBitmaps [bD1])
	return 0;
if (bitmapOffsets [bD1][bmi] == 0)
	return 0;		// A read-from-disk bmi!!!

#if DBG
if (bmi == nDbgTexture)
	nDbgTexture = nDbgTexture;
#endif
bmP = &gameData.pig.tex.bitmaps [bD1][bmi];
if ((bmoP = bmP->Override ()))
	bmP = bmoP;
while (0 > (i = PageInBitmap (bmP, gameData.pig.tex.bitmapFiles [bD1][bmi].name, bmi, bD1, bHires)))
	G3_SLEEP (0);
if (!i)
	return 0;
gameData.pig.tex.bitmaps [bD1][bmi].DelFlags (BM_FLAG_PAGED_OUT);
return 1;
}
Beispiel #21
0
void WaitForSoundThread (void)
{
//time_t t1 = SDL_GetTicks ();
while (tiSound.ti.pThread && tiSound.ti.bExec /*&& (SDL_GetTicks () - t1 < 1000)*/)
	G3_SLEEP (1);
}
int _CDECL_ RenderThread (void *pThreadId)
{
    int		nId = *reinterpret_cast<int*> (pThreadId);
    int		nStart, nEnd;
#ifdef _WIN32
    HGLRC		myContext = 0;
#endif

    do {
        while (!tiRender.ti [nId].bExec) {
            G3_SLEEP (0);
            if (tiRender.ti [nId].bDone)
                return 0;
        }
        if (tiRender.nTask == rtSortSegZRef) {
            ComputeThreadRange (nId, gameData.render.mine.nRenderSegs, nStart, nEnd);
            QSortSegZRef (nStart, nEnd);
        }
        else if (tiRender.nTask == rtInitSegZRef) {
            ComputeThreadRange (nId, gameData.render.mine.nRenderSegs, nStart, nEnd);
            InitSegZRef (nStart, nEnd, nId);
        }
        else if (tiRender.nTask == rtStaticVertLight) {
            ComputeThreadRange (nId, gameData.segs.nVertices, nStart, nEnd);
            lightManager.GatherStaticVertexLights (nStart, nEnd, nId);
        }
        else if (tiRender.nTask == rtComputeFaceLight) {
            if (gameStates.render.bTriangleMesh || !gameStates.render.bApplyDynLight || (gameData.render.mine.nRenderSegs < gameData.segs.nSegments)) {
                // special handling:
                // tiMiddle is the index at which an equal number of visible faces is both at indices below and above it
                // use it to balance thread load
                if (gameStates.app.nThreads & 1) {
                    ComputeThreadRange (nId, gameData.render.mine.nRenderSegs, nStart, nEnd);
                    ComputeFaceLight (nStart, nEnd, nId);
                }
                else {
                    int nPivot = gameStates.app.nThreads / 2;
                    if (nId < nPivot) {
                        ComputeThreadRange (nId, tiRender.nMiddle, nStart, nEnd, nPivot);
                        ComputeFaceLight (nStart, nEnd, nId);
                    }
                    else {
                        ComputeThreadRange (nId - nPivot, gameData.render.mine.nRenderSegs - tiRender.nMiddle, nStart, nEnd, nPivot);
                        ComputeFaceLight (nStart + tiRender.nMiddle, nEnd + tiRender.nMiddle, nId);
                    }
                }
            }
            else {
                if (gameStates.app.bEndLevelSequence < EL_OUTSIDE)
                    ComputeThreadRange (nId, gameData.segs.nFaces, nStart, nEnd);
                else
                    ComputeThreadRange (nId, gameData.segs.nSegments, nStart, nEnd);
                ComputeFaceLight (nStart, nEnd, nId);
            }
        }
        else if (tiRender.nTask == rtPolyModel) {
            short	iVerts, nVerts, iFaceVerts, nFaceVerts;

            if (nId) {
                nVerts = tiRender.pm->m_nVerts;
                iVerts = nVerts / 2;
                nFaceVerts = tiRender.pm->m_nFaceVerts;
                iFaceVerts = nFaceVerts / 2;
            }
            else {
                iVerts = 0;
                nVerts = tiRender.pm->m_nVerts / 2;
                iFaceVerts = 0;
                nFaceVerts = tiRender.pm->m_nFaceVerts / 2;
            }
            G3DynLightModel (tiRender.objP, tiRender.pm, iVerts, nVerts, iFaceVerts, nFaceVerts);
        }
        else if (tiRender.nTask == rtLightmap)
            lightmapManager.Build (nId);
        else if (tiRender.nTask == rtParticles)
            particleManager.SetupParticles (nId);
        tiRender.ti [nId].bExec = 0;
    } while (!tiRender.ti [nId].bDone);
#ifdef _WIN32
    if (myContext)
        wglDeleteContext (myContext);
#endif
    return 0;
}
Beispiel #23
0
//Process selected keys until game unpaused. returns key that left pause (p or esc)
int DoGamePause (void)
{
	int			key = 0;
	int			bScreenChanged;
	char			msg [1000];
	char			totalTime [9], xLevelTime [9];

if (gameData.app.bGamePaused) {		//unpause!
	gameData.app.bGamePaused = 0;
	gameStates.app.bEnterGame = 1;
#if defined (TACTILE)
	if (TactileStick)
		EnableForces();
#endif
	return KEY_PAUSE;
	}

if (gameData.app.nGameMode & GM_NETWORK) {
	 DoShowNetgameHelp();
    return (KEY_PAUSE);
	}
else if (gameData.app.nGameMode & GM_MULTI) {
	HUDInitMessage (TXT_MODEM_PAUSE);
	return (KEY_PAUSE);
	}
PauseGame ();
SetPopupScreenMode ();
paletteManager.LoadEffect ();
formatTime (totalTime, X2I (LOCALPLAYER.timeTotal) + LOCALPLAYER.hoursTotal * 3600);
formatTime (xLevelTime, X2I (LOCALPLAYER.timeLevel) + LOCALPLAYER.hoursLevel * 3600);
  if (gameData.demo.nState!=ND_STATE_PLAYBACK)
	sprintf (msg, TXT_PAUSE_MSG1, GAMETEXT (332 + gameStates.app.nDifficultyLevel), 
			   LOCALPLAYER.hostages.nOnBoard, xLevelTime, totalTime);
   else
	  	sprintf (msg, TXT_PAUSE_MSG2, GAMETEXT (332 +  gameStates.app.nDifficultyLevel), 
				   LOCALPLAYER.hostages.nOnBoard);

if (!gameOpts->menus.nStyle) {
	gameStates.menus.nInMenu++;
	GameRenderFrame ();
	gameStates.menus.nInMenu--;
	}
messageBox.Show (pszPauseMsg = msg, false);	
GrabMouse (0, 0);
while (gameData.app.bGamePaused) {
	if (!(gameOpts->menus.nStyle && gameStates.app.bGameRunning))
		key = KeyGetChar();
	else {
		gameStates.menus.nInMenu++;
		while (!(key = KeyInKey ())) {
			GameRenderFrame ();
			paletteManager.LoadEffect (NULL);
			messageBox.Render ();
			G3_SLEEP (1);
			}
		gameStates.menus.nInMenu--;
		}
#if DBG
		HandleTestKey(key);
#endif
		bScreenChanged = HandleSystemKey (key);
		HandleVRKey (key);
		if (bScreenChanged) {
			GameRenderFrame ();
			messageBox.Render ();
#if 0		
			show_extraViews ();
			if ((gameStates.render.cockpit.nType == CM_FULL_COCKPIT) || (gameStates.render.cockpit.nType == CM_STATUS_BAR))
				RenderGauges();
#endif			
			}
	}
GrabMouse (1, 0);
messageBox.Clear ();
ResumeGame ();
return key;
}
Beispiel #24
0
short TerminateWinsock ()
{
    G3_SLEEP(50);
    G3_SLEEP(50);
    return (WSACleanup() == SOCKET_ERROR ? WSAGetLastError () : 0);
}
Beispiel #25
0
void CalcFrameTime (void)
{
if (gameData.app.bGamePaused) {
	gameData.time.xLast = TimerGetFixedSeconds ();
	gameData.time.xFrame = 0;
	gameData.time.xRealFrame = 0;
	return;
	}

fix 	timerValue,
		xLastFrameTime = gameData.time.xFrame;
GetSlowTicks ();

#if EXACT_FRAME_TIME

	static float fSlack = 0;

	int	nFrameTime, nMinFrameTime, nDeltaTime;

if (MAXFPS <= 1) 
	nDeltaTime = 0;
else {
#ifdef RELEASE
	if (!gameOpts->app.bExpertMode && (gameOpts->render.nMaxFPS > 1))
		gameOpts->render.nMaxFPS = MAX_FRAMERATE;
#endif
	if (!gameData.time.tLast)
		nDeltaTime = 0;
	else {
		nFrameTime = gameStates.app.nSDLTicks - gameData.time.tLast;
		nMinFrameTime = 1000 / MAXFPS;
		nDeltaTime = nMinFrameTime - nFrameTime;
		fSlack += 1000.0f / MAXFPS - nMinFrameTime;
		if (fSlack >= 1) {
			nDeltaTime += int (fSlack);
			fSlack -= int (fSlack);
			}
		if (0 < nDeltaTime)
			G3_SLEEP (nDeltaTime);
		}
	}
timerValue = MSEC2X (gameStates.app.nSDLTicks);

#else

fix xMinFrameTime = ((MAXFPS > 1) ? I2X (1) / MAXFPS : 1);
do {
	timerValue = TimerGetFixedSeconds ();
   gameData.time.xFrame = timerValue - gameData.time.xLast;
	if (MAXFPS < 2)
		break;
	G3_SLEEP (1);
	} while (gameData.time.xFrame < xMinFrameTime);

#endif

gameData.time.xFrame = timerValue - gameData.time.xLast;
gameData.time.xRealFrame = gameData.time.xFrame;
if (gameStates.app.cheats.bTurboMode)
	gameData.time.xFrame *= 2;
gameData.time.xLast = timerValue;

#if EXACT_FRAME_TIME

gameData.time.tLast = gameStates.app.nSDLTicks;
if (nDeltaTime > 0)
	gameData.time.tLast += nDeltaTime;

#else

gameData.time.tLast = SDL_GetTicks ();

#endif

if (gameData.time.xFrame < 0)						//if bogus frametimed:\temp\dm_test.
	gameData.time.xFrame = xLastFrameTime;		//d:\temp\dm_test.then use time from last frame
#if Arcade_mode
gameData.time.xFrame /= 2;
#endif
#if defined (TIMER_TEST) && defined (_DEBUG)
gameData.time.xStops = gameData.time.xStarts = 0;
#endif
//	Set value to determine whether homing missile can see target.
//	The lower frametime is, the more likely that it can see its target.
if (gameStates.limitFPS.bHomers)
	xMinTrackableDot = MIN_TRACKABLE_DOT;
else if (gameData.time.xFrame <= I2X (1)/64)
	xMinTrackableDot = MIN_TRACKABLE_DOT;	// -- 3* (I2X (1) - MIN_TRACKABLE_DOT)/4 + MIN_TRACKABLE_DOT;
else if (gameData.time.xFrame < I2X (1)/32)
	xMinTrackableDot = MIN_TRACKABLE_DOT + I2X (1)/64 - 2*gameData.time.xFrame;	// -- FixMul (I2X (1) - MIN_TRACKABLE_DOT, I2X (1)-4*gameData.time.xFrame) + MIN_TRACKABLE_DOT;
else if (gameData.time.xFrame < I2X (1)/4)
	xMinTrackableDot = MIN_TRACKABLE_DOT + I2X (1)/64 - I2X (1)/16 - gameData.time.xFrame;	// -- FixMul (I2X (1) - MIN_TRACKABLE_DOT, I2X (1)-4*gameData.time.xFrame) + MIN_TRACKABLE_DOT;
else
	xMinTrackableDot = MIN_TRACKABLE_DOT + I2X (1)/64 - I2X (1)/8;
}
Beispiel #26
0
//if filename passed is NULL, show Normal credits
void ShowCredits(char *credits_filename)
{
	int			i, j, l, bDone;
	CFile			cf;
	char			buffer [NUM_LINES_HIRES][80];
	grsBitmap	bmBackdrop;
	int			nPcxError;
	unsigned int	nLine = 0;
	unsigned int	nXlLine = 0;
	fix			xTimeout, xDelay = X2I (2800 * 1000);
	int			nFirstLineOffs, nExtraInc = 0;
	int			bBinary = 0;
	char			*pszTemp;
	char			filename [32];
	int			xOffs, yOffs;
	box			dirtyBox [NUM_LINES_HIRES];
	gsrCanvas	*creditsOffscreenBuf = NULL;
	gsrCanvas	*saveCanv = grdCurCanv;

	// Clear out all tex buffer lines.
memset (buffer, 0, sizeof (buffer));
memset (dirtyBox, 0, sizeof (dirtyBox));

sprintf(filename, "%s", CREDITS_FILE);
bBinary = 0;
if (credits_filename) {
	strcpy(filename,credits_filename);
	bBinary = 1;
	}
if (!cf.Open (filename, gameFolders.szDataDir, "rb", 0)) {
	char nfile [32];

	if (credits_filename)
		return;		//ok to not find special filename

	if ((pszTemp = strchr (filename, '.')))
		*pszTemp = '\0';
	sprintf (nfile, "%s.txb", filename);
	if (!cf.Open (nfile, gameFolders.szDataDir, "rb", 0))
		Error("Missing CREDITS.TEX and CREDITS.TXB &cf\n");
	bBinary = 1;
	}
SetScreenMode(SCREEN_MENU);
xOffs = (grdCurCanv->cvBitmap.bmProps.w - 640) / 2;
yOffs = (grdCurCanv->cvBitmap.bmProps.h - 480) / 2;
if (xOffs < 0)
	xOffs = 0;
if (yOffs < 0)
	yOffs = 0;
creditsPalette = GrUsePaletteTable("credits.256", NULL);
GrPaletteStepLoad (NULL);
header_font = GrInitFont(gameStates.menus.bHires ? (char *) "font1-1h.fnt" : (char *) "font1-1.fnt");
title_font = GrInitFont(gameStates.menus.bHires ? (char *) "font2-3h.fnt" : (char *) "font2-3.fnt");
names_font = GrInitFont(gameStates.menus.bHires ? (char *) "font2-2h.fnt" : (char *) "font2-2.fnt");
bmBackdrop.bmTexBuf = NULL;
bmBackdrop.bmPalette = NULL;

//MWA  Made bmBackdrop bitmap linear since it should always be.  the current canvas may not
//MWA  be linear, so we can't rely on grdCurCanv->cvBitmap->bmProps.nType.

nPcxError = PCXReadBitmap ((char *) CREDITS_BACKGROUND_FILENAME, &bmBackdrop, BM_LINEAR, 0);
if (nPcxError != PCX_ERROR_NONE) {
	cf.Close();
	return;
	}
SongsPlaySong(SONG_CREDITS, 1);
GrRemapBitmapGood(&bmBackdrop, NULL, -1, -1);

if (!gameOpts->menus.nStyle) {
	GrSetCurrentCanvas(NULL);
	GrBitmap(xOffs,yOffs,&bmBackdrop);
	if ((grdCurCanv->cvBitmap.bmProps.w > 640) || (grdCurCanv->cvBitmap.bmProps.h > 480)) {
		GrSetColorRGBi (RGBA_PAL (0,0,32));
		GrUBox(xOffs,yOffs,xOffs+bmBackdrop.bmProps.w+1,yOffs+bmBackdrop.bmProps.h+1);
		}
	}
GrPaletteFadeIn(NULL, 32, 0);

//	Create a new offscreen buffer for the credits screen
//MWA  Let's be a little smarter about this and check the VR_offscreen buffer
//MWA  for size to determine if we can use that buffer.  If the game size
//MWA  matches what we need, then lets save memory.

if (gameStates.menus.bHires && !gameOpts->menus.nStyle && gameStates.render.vr.buffers.offscreen->cv_w == 640)
	creditsOffscreenBuf = gameStates.render.vr.buffers.offscreen;
else if (gameStates.menus.bHires)
	creditsOffscreenBuf = GrCreateCanvas(640,480);
else
	creditsOffscreenBuf = GrCreateCanvas(320,200);
if (!creditsOffscreenBuf)
	Error("Not enough memory to allocate Credits Buffer.");
creditsOffscreenBuf->cvBitmap.bmPalette = grdCurCanv->cvBitmap.bmPalette;
if (gameOpts->menus.nStyle)
	creditsOffscreenBuf->cvBitmap.bmProps.flags |= BM_FLAG_TRANSPARENT;
KeyFlush ();

bDone = 0;
nFirstLineOffs = 0;

xTimeout = SDL_GetTicks () + xDelay;
glEnable (GL_BLEND);
glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
gameStates.menus.nInMenu = 1;
while (1) {
	int k;

	do {
		nLine = (nLine + 1) % NUM_LINES;
get_line:;
		if (cf.GetS (buffer [nLine], 80)) {
			char *p = buffer [nLine];
			if (bBinary)				// is this a binary tbl &cf
				for (i = (int) strlen (buffer [nLine]); i > 0; i--, p++)
					*p = EncodeRotateLeft ((char) (EncodeRotateLeft (*p) ^ BITMAP_TBL_XOR));
			p = buffer [nLine];
			if (*p == ';')
				goto get_line;
			if (*p == '%') {
				if (p [1] == ALLOWED_CHAR)
					strcpy (p, p + 2);
				else
					goto get_line;
				}
			if ((p = strchr (buffer [nLine], '\n')))
				*p = '\0';
			} 
		else if (nXlLine < NUM_XL_LINES) {
			strcpy (buffer [nLine], xlCredits [nXlLine++]);
			}
		else {
			//fseek(&cf, 0, SEEK_SET);
			buffer [nLine][0] = 0;
			bDone++;
			}
		} while (nExtraInc--);
	nExtraInc = 0;

	//PrintLog ("%s\n", buffer [nLine]);
	for (i = 0; i < ROW_SPACING; i += gameStates.menus.bHires + 1) {
		int y;

		if (gameOpts->menus.nStyle) {
			GrSetCurrentCanvas (NULL);
			ShowFullscreenImage (&bmBackdrop);
	//			GrUpdate (0);
	#if 0
			if ((grdCurCanv->cvBitmap.bmProps.w > 640) || (grdCurCanv->cvBitmap.bmProps.h > 480)) {
				GrSetColorRGBi (RGBA_PAL (0,0,32));
				GrUBox (xOffs, yOffs, xOffs + bmBackdrop. bmProps.w + 1, yOffs + bmBackdrop.bmProps.h + 1);
				}
	#endif
			}
		y = nFirstLineOffs - i;
		GrSetCurrentCanvas (creditsOffscreenBuf);
		if (gameOpts->menus.nStyle)
			GrClearCanvas (0);	
		else
			GrBitmap (0, 0, &bmBackdrop);
		for (j = 0; j < NUM_LINES; j++)	{
			char *s;

			l = (nLine + j + 1) %  NUM_LINES;
			s = buffer [l];
			if (s[0] == '!') 
				s++;
			else if (s[0] == '$') {
				grdCurCanv->cvFont = header_font;
				s++;
				} 
			else if (s[0] == '*') {
				grdCurCanv->cvFont = title_font;
				s++;
				} 
			else
				grdCurCanv->cvFont = names_font;
			grBitBltFadeTable = (gameStates.menus.bHires ? fadeValues_hires : fadeValues);
			pszTemp = strchr (s, '\t');
			if (pszTemp) {	//	Wacky Credits thing
				int w, h, aw, w2, x1, x2;
				*pszTemp = 0;
				GrGetStringSize(s, &w, &h, &aw);
				x1 = ((gameStates.menus.bHires?320:160)-w)/2;
				cr_gr_printf (x1 , y, s);
				GrGetStringSize (pszTemp + 1, &w2, &h, &aw);
				x2 = (gameStates.menus.bHires ? 320 : 160) + (((gameStates.menus.bHires ? 320 : 160) - w2) / 2);
				cr_gr_printf(x2, y, &pszTemp[1]);
				dirtyBox [j].left = ((gameStates.menus.bHires?320:160)-w)/2;
				dirtyBox [j].top = y;
				dirtyBox [j].width =(x2+w2)-x1;
				dirtyBox [j].height = h;
				*pszTemp = '\t';
				} 
			else {
			// Wacky Fast Credits thing
				int w, h, aw;

				GrGetStringSize (s, &w, &h, &aw);
				dirtyBox [j].width = w;
        		dirtyBox [j].height = h;
        		dirtyBox [j].top = y;
        		dirtyBox [j].left = ((gameStates.menus.bHires?640:320) - w) / 2;
				cr_gr_printf (0x8000, y, s);
				}
			grBitBltFadeTable = NULL;
			if (buffer[l][0] == '!')
				y += ROW_SPACING / 2;
			else
				y += ROW_SPACING;
			}

		if (gameOpts->menus.nStyle) 
			GrSetCurrentCanvas (NULL);

		{	// Wacky Fast Credits Thing
		box	*newBox;
		grsBitmap *tempBmP;

		for (j = 0; j < NUM_LINES; j++) {
			newBox = dirtyBox + j;
			tempBmP = &creditsOffscreenBuf->cvBitmap;

			GrBmBitBlt (newBox->width + 1, newBox->height +4,
							newBox->left + xOffs, newBox->top + yOffs, 
							newBox->left, newBox->top,
							tempBmP, &grdCurScreen->scCanvas.cvBitmap);
			}
		}
	GrUpdate (0);
#if 1
	{
	int t = xTimeout - SDL_GetTicks ();
	if (t > 0)
		G3_SLEEP (t);
	xTimeout = SDL_GetTicks () + xDelay;
	}
#endif
	//see if redbook song needs to be restarted
	SongsCheckRedbookRepeat();
	k = KeyInKey ();
#if DBG
	if (k == KEY_BACKSP) {
		Int3();
		k = 0;
		}
#endif

	if ((k == KEY_PRINT_SCREEN) || (k == KEY_ALTED+KEY_F9)) {
		gameStates.app.bSaveScreenshot = 1;
		SaveScreenShot (NULL, 0);
		k = 0;
		}
	else if (k == KEY_PADPLUS)
		xDelay /= 2;
	else if (k == KEY_PADMINUS) {
		if (xDelay)
			xDelay *= 2;
		else
			xDelay = 1;
		}
	else if ((k == KEY_ESC) || (bDone > NUM_LINES)) {
		GrCloseFont (header_font);
		GrCloseFont (title_font);
		GrCloseFont (names_font);
		GrPaletteFadeOut (NULL, 32, 0);
		GrUsePaletteTable (D2_DEFAULT_PALETTE, NULL);
		D2_FREE (bmBackdrop.bmTexBuf);
		cf.Close ();
		GrSetCurrentCanvas (saveCanv);
		SongsPlaySong (SONG_TITLE, 1);

		if (creditsOffscreenBuf != gameStates.render.vr.buffers.offscreen)
			GrFreeCanvas (creditsOffscreenBuf);
		glDisable (GL_BLEND);
		gameStates.menus.nInMenu = 0;
		return;
		}
	}

	if (buffer [(nLine + 1) %  NUM_LINES][0] == '!') {
		nFirstLineOffs -= ROW_SPACING - ROW_SPACING / 2;
		if (nFirstLineOffs <= -ROW_SPACING) {
			nFirstLineOffs += ROW_SPACING;
			nExtraInc++;
			}
		}
	}
}