2013-09-03 7 views
0

J'ai simple boucle de jeu en java:Comportement étrange de la boucle jeu java

public void run(){ 
    while(running){ 
     start = System.nanoTime(); 
     gamePanel.update(); 
     gamePanel.repaint(); 
     elapsed = System.nanoTime() - start; 
     wait = (TARGET_TIME - elapsed)/1000000; 
     if(wait < 0){wait = TARGET_TIME;} 
     try {Thread.sleep(wait);}catch(Exception e) {e.printStackTrace();} 
    } 
} 

Maintenant le problème: Quand j'ajouter une sysout dans la mise à jour() sortie « mise à jour » et un en paintComponent() sortie " repeindre », je me le résultat suivant:

updating 
updating 
updating 
updating 
updating 
(x1000 and more) 
repainting 

Alors quand je repeindre une fois, le jeu est mise à jour 1000 et plus de fois. Est-ce normal? Je pense que c'est abit étrange, n'est-ce pas? Par exemple, peut faire 1000 pas avec le joueur jusqu'à ce que le jeu le peigne ... Cela signifie que la méthode update() n'attend pas de repeindre la finition? Pourquoi?

Merci!

Edit: Voici le code de mise à jour:

public void update(){ 
    if(moveUp){ 
     changeMapY(map, -map.getSpeed()); 
    } 
    if(moveDown){ 
     changeMapY(map, map.getSpeed()); 
    } 
    if(moveRight){ 
     changeMapX(map, map.getSpeed()); 
    } 
    if(moveLeft){ 
     changeMapX(map, -map.getSpeed()); 
    } 
} 

Edit 2: Et voici ce changeMap fait: (peut-être c'est le problème)

public void changeMapX(Map map, int amount){ 
    for(int i = 0; i < blocks.length; i++){ 
     for(int j = 0; j < blocks[0].length; j++){ 
      blocks[i][j].addX(amount); 
     } 
    } 
    map.addOffsetx(amount); 
} 

public void changeMapY(Map map, int amount){ 
    for(int i = 0; i < blocks.length; i++){ 
     for(int j = 0; j < blocks[0].length; j++){ 
      blocks[i][j].addY(amount); 
     } 
    } 
    map.addOffsety(amount); 
} 
+0

Peut-être que vous avez une boucle dans 'gamePanel.update();', qui affiche 'update' 1000 fois? – Pawel

+0

@Pawel non je n'ai pas. –

+0

Pourrions-nous voir une partie du code dans la mise à jour? (Je suppose que la mise à jour n'est pas non plus récursive?) – Jordan

Répondre

0

Vous calculez attendre en quelques secondes. (nano-seconde/1 million)

Le paramètre à mettre en veille doit être en millisecondes. Donc, changez cette ligne:

wait = (TARGET_TIME - elapsed)/1000; 
+0

C'est vrai, mais ça ne répond pas à la question, n'est-ce pas? – Fildor

+0

@Fildor S'il attend 1/1000ème aussi longtemps qu'il le devrait avant de revenir en arrière, la boucle sera exécutée 1000 fois plus souvent. Je pense que cela constitue une réponse. –

+0

Hmmm ça va, parce que c'est bon et ça aide ... Maintenant, il met à jour 1 à 3 fois en redessinant 1 fois. Mais de toute façon, la méthode de mise à jour ne fonctionne pas ... –

0

J'ai testé votre code source et "mise à jour", "repeindre" sont l'un après l'autre. Le problème est lié à votre méthode update(). Peut-être récursif, peut-être en boucle.

+0

regardez ma deuxième édition, c'est peut-être le problème? –

+0

@ T_01 encore je ne vois pas de problème dans votre code source. – Pawel

0

En supposant que gamePanel est un composant Swing, ce que vous observez probablement est que repaint() n'appelle pas réellement JComponent.paintComponent(). Tout ce qu'il fait est essentiellement invalide les graphiques du composant et dit à Swing de repeindre le composant à un moment futur, sur le thread Swing.

Les appels multiples à repaint() n'aboutissent pas nécessairement à plusieurs appels à paintComponent() - les demandes de repeint redondantes sont regroupées en une seule.

+0

repaint appelle paintComponent bien sûr, et paintComponent appelle super.paintComponents(); –

+0

L'implémentation par défaut de repaint() ne l'est pas. Si vous l'annulez, il serait utile de le mentionner. – TrogDor

Questions connexes