Comment faire une boucle d'affichage du rendu 3d ou 2d

Contenu du snippet

Dans tous les programmes créant une scène graphique, il y'a la mise en place d'une boucle principale, qui tourne en permanence quelle que soit l'action de l'utilisateur. Mais si la fenêtre du rendu du graphique est réduite, ou masquée par un autre programme, il est inutile de continuer à la rafraîchir, puisque l'utilisateur ne la voit pas. Car dans ce cas, on prend des ressources qui seraient utiles aux autres programmes.
J'ai vu plusieurs procédés pour arrêter temporairement la boucle, en utilisant un timer, ou en paramétrant une pause avec la seule subroutine "sleep", ou carrément en stoppant la boucle de rendu pour la réinitialiser lorsque la fenêtre revient au premier plan.
le DoEvents lance le système dans une boucle à vide pour voir si un autre processus a besoin de ressources aussi. Mais dans le cas ou le jeu est en pause, le DoEvents s'exécute plusieurs milliers de fois par seconde, monopolisant aussi les ressources. D'où la mise en place d'un retard qui le fait s'exécuter une seule fois par seconde.
A terme, j'ai établi cette façon de gérer la boucle, pour rester simple.

Source / Exemple :


Public bActif As Boolean
' Cette variable va nous permette de rendre active la boucle et de déterminer
' si le programme exécute le rendu. ' Lancement du rendu dans le Sub form_load() par exemple:
'    bActif = True

Public Declare Function GetActiveWindow Lib "user32" () As Long
'Cette fonction donne le hWnd de la fenêtre actuellement active à l'écran. Si la fenêtre du jeu est différente 
'(elle est cachée), inutile de la rafraîchir pour économiser les ressources du système.

Declare Sub Sleep Lib "kernel32" Alias "Sleep" (ByVal dwMilliseconds As Long)
'pause en milli-secondes

Sub Main()

	-----------------------------------------------------------------------------------------
	Ici mettre les opérations qui ne s'exécutent qu'une fois au bébut, comme Init3D(),
	remplissage des matrices, initialisation de la caméra ...
	-----------------------------------------------------------------------------------------

	Form1.Show	'présentation de la feuille

	' Ici, on met la boucle principale du jeu.

	While bActif

    	d3dDevice.Clear 0, ByVal 0, D3DCLEAR_TARGET, &HFF000000, 1#, 0 'on efface

	-----------------------------------------------------------------------------------------
	Ici mettre les calculs en temps réel, qui ne s'arrêtent pas même si la fenêtre n'est pas
	visible, et qui sont fonction du passage du temps dans le jeu.
	-----------------------------------------------------------------------------------------

If GetActiveWindow = FEtudeDX8.hWnd Then 'Ici on teste si notre fenetre est affichée
	'si la page n'est pas visible, inutile de la recalculer pour économiser les
	'ressources de l'ordinateur.
  
'- Création de la scène -
 
	d3dDevice.BeginScene

	-----------------------------------------------------------------------------------------
	mettre ici tout ce qui concerne le rendu comme d3dDevice.SetTexture
	-----------------------------------------------------------------------------------------
    	
	d3dDevice.EndScene
    
	'- On affiche la scène: -
	d3dDevice.Present ByVal 0, ByVal 0, 0, ByVal 0  ' Equivaut la fonction Flip dans DirectX 7

Else
        'si la fenêtre n'est pas visible, pas de rendu.
	sleep (1000) 'retard 1 seconde
End If
          
        DoEvents    ' Le système va exécuter des tâches en attente... (Ne pas l'effacer sous peine de blocages...)
   
    Wend

        ' IMPORTANT : avant de fermer le programme, il faut absolument décharger
        '  les objets de la mémoire :
        
        Set d3d = Nothing       ' on décharge l'objet principal Direct3D
        Set d3dDevice = Nothing ' -- -------- ------- contenant le plan de la scène
        Set d3dVB = Nothing     ' -- -------- ------- stockant les vecteurs
        Set dx = Nothing        ' -- -------- ------- Direct X

    End     'on arrête le programme

End Sub

Conclusion :


Ainsi, on peut économiser les ressources au moment des rendus inutiles, tout en gardant l'écoulement du temps dans le jeu, que l'utilisateur regarde la fenêtre ou pas.

A voir également

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.