Java 2D Drawing performance optimale

je suis en train d'écrire un jeu Java 2D. J'utilise les bibliothèques de dessin Java 2D intégrées, en dessinant sur un Graphics2D que j'obtiens à partir d'une stratégie de buffers à partir d'une toile dans un JFrame (qui est parfois entièrement filtré). Le BufferStrategy est à double tampon. Repeindre est fait activement, via un minuteur. J'ai quelques problèmes de performance, surtout sur Linux.

et Java2D a tellement de façons de créer des tampons graphiques et des graphiques de dessin que je juste ne sais pas si je suis en train de faire la bonne chose. J'ai fait des expériences avec graphics2d.getDeviceConfiguration ().createCompatibleVolatileImage, qui semble prometteur, mais je n'ai pas de vraie preuve que ce sera plus rapide si je passe le code de dessin à cela.

d'après votre expérience, Quel est le moyen le plus rapide de rendre des graphiques 2D sur L'écran en Java 1.5+? Notez que le jeu est très en avance, donc je ne veux pas passer à une méthode de dessin complètement différente, comme OpenGL ou un moteur de jeu. Je veux essentiellement savoir comment obtenir le moyen le plus rapide d'utiliser un objet Graphics2D pour dessiner des trucs à l'écran.

31
demandé sur Zarkonnen 2008-09-29 16:32:30

9 réponses

j'ai les mêmes problèmes que vous, je pense. Regardez mon billet ici:

Java2D Des Problèmes De Performances

montre la raison de la dégradation de la performance et comment la corriger. Il n'est pas garanti de bien fonctionner sur toutes les plateformes. Vous verrez pourquoi dans le post.

15
répondu Consty 2017-05-23 11:45:29

Une synthèse des réponses à ce post, les réponses à Consty , et de ma propre recherche:

Ce qui fonctionne:

  • utilisez GraphicsConfiguration.createCompatibleImage pour créer des images compatibles avec ce que vous dessinez. C'est absolument essentiel!
  • utiliser un dessin à double tampon via Canvas.createBufferStrategy .
  • utiliser -Dsun.java2d.opengl=True si disponible pour accélérer le dessin.
  • Évitez d'utiliser des transformes pour la mise à l'échelle. Au lieu de cela, cache les versions à l'échelle des images que vous allez utiliser.
  • évitez les images translucides! Les images Bitmasked sont très bien, mais la translucidité est très chère en Java2D.

dans mes tests, en utilisant ces méthodes, j'ai obtenu une augmentation de vitesse de 10x - 15x, ce qui rend les graphiques Java 2D appropriés une possibilité.

29
répondu Zarkonnen 2017-05-23 11:45:29

Voici quelques conseils sur le dessus de ma tête. Si vous étiez plus spécifique et que vous essayiez de faire, je peut être en mesure d'aider plus. Sonne comme un jeu, mais je ne veux pas assumer.

ne dessinez que ce dont vous avez besoin! Ne pas appeler aveuglément repaint () tout le temps, essayer certains des frères et sœurs comme repaint(Rect) ou repaint (x,y,w,h).

soyez très prudent avec le mélange alpha car il peut être une opération coûteuse pour mélanger des images / primitives.

essayez de prerender / cache autant que possible. Si vous vous trouvez à dessiner un cercle de la même façon, encore et encore, envisagez de dessiner dans un tampon et puis juste dessiner le tampon. Vous êtes sacrifier la mémoire pour la vitesse (typique des jeux / haute perf graphiques)

envisager D'utiliser OpenGL, utiliser JOGL de LWJGL. JOGL est plus Java alors que LWJGL offre plus de fonctionnalités de jeu en plus de L'accès OpenGL. OpenGL peut tirer des ordres de grandeur (avec le matériel et les pilotes appropriés) que Swing peut.

10
répondu basszero 2008-10-01 11:50:38

il y en a un important qui n'a pas encore été mentionné, je pense: des images de cache de tout ce que vous pouvez. Si vous avez un objet qui se déplace à travers l'écran, et c'est l'apparence ne change pas beaucoup, dessiner une image, puis le rendu de l'image à l'écran dans une nouvelle position de chaque image. Le faire même si l'objet est très simple: vous pourriez être surpris de voir combien de temps vous enregistrer. Rendre un bitmap est beaucoup plus rapide que rendre des primitives.

You pourrait également vouloir examiner la mise en place des conseils de rendu explicitement, et désactiver des choses comme antialiasing si les considérations de qualité permettent.

3
répondu DJClayworth 2009-05-01 19:11:00

j'ai fait quelques applications de dessin de base en utilisant Java. Je n'ai pas travaillé sur quelque chose de trop graphique-intensif, mais je recommanderais que vous ayez une bonne poignée sur toutes les invocations "repeat". Un appel de repeindre supplémentaire sur un conteneur parent pourrait doubler la quantité de rendu de votre action.

1
répondu Brendan Cashman 2008-09-29 12:50:44

j'ai regardé cette question en espérant que quelqu'un vous offrir une meilleure réponse que la mienne.

dans l'intervalle, j'ai trouvé le suivant Sun white paper qui a été écrit après une version bêta de JDK 1.4. Il y a quelques recommandations intéressantes ici sur le réglage fin, y compris les indicateurs d'exécution (en bas de l'article):

drapeau D'exécution pour Solaris et Linux

à partir de la version bêta 3 du SDK, Version 1.4, Java 2D stocke les images en pixmaps par défaut lorsque DGA n'est pas disponible, que vous travailliez dans un environnement d'affichage local ou distant. Vous pouvez modifier ce comportement avec le drapeau pmoffscreen:

- Dsun.java2d.pmoffscreen=true /false

si vous positionnez ce drapeau à true, le support pixmap est activé même si DGA est disponible. Si vous mettez ce drapeau à false, Offscreen pixmap le support est désactivé. désactiver le support pixmap Offscreen peut résoudre certains problèmes de rendu. "

1
répondu Brendan Cashman 2016-01-03 10:53:07

assurez-vous d'utiliser le double buffering, de dessiner, d'abord à une grande mémoire tampon, puis rincer à l'écran lorsque le dessin est terminé.

0
répondu Tom 2008-09-29 12:37:30

Il y a quelques choses que vous devez garder à l'esprit

1) est rafraîchissant ce lien montre comment utiliser swingtimers qui pourrait être une bonne option pour appeler repaint. Se repeindre compris (comme les affiches précédentes ont dit est important de sorte que vous ne faites pas trop de travail).

2) Assurez-vous que vous faites seulement le dessin dans un fil. La mise à jour de L'UI à partir de threads mulitple peut conduire à des choses désagréables.

3) Double Tampon. Cela rend le rendu plus lisse. ce site a des informations supplémentaires à vous communiquer

0
répondu Steve g 2008-09-29 13:17:21

une alternative si vous ne voulez pas aller pur Java 2D est d'utiliser une bibliothèque de jeux tels que GTGE ou JGame (cherchez-les sur Google), puis offrir un accès facile aux graphiques et offrent également un double tampon et des commandes de dessin beaucoup plus simple.

0
répondu Paul Sagor 2008-11-17 05:22:21