Java Panneau Double Mise En Mémoire Tampon
demandais si quelqu'un pouvait me diriger dans la bonne directon, j'ai développé un jeu de pong et il a besoin de la double mise en tampon en raison de scintillement. Iv essayé certains de le poster ici pour essayer de le faire fonctionner, mais je suis encore un débutant avec le swing, awt suff, toute aide serait étonnant grâce.
public class PongPanel extends JPanel implements Runnable {
private int screenWidth = 500;
private int screenHeight = 300;
private boolean isPaused = false;
private boolean isGameOver = false;
private int playToPoints = 10;
private Padel player1,player2;
private Ball ball;
private Thread gameThread;
private Image dbImage;
private Graphics dbg;
public PongPanel() {
setPreferredSize(new Dimension(screenWidth,screenHeight));
setBackground(Color.BLACK);
setDoubleBuffered(true);
setFocusable(true);
requestFocus();
player1 = new Padel(Position.LEFT,screenWidth,screenHeight);
player2 = new Padel(Position.RIGHT,screenWidth,screenHeight);
ball = new Ball(10,screenWidth/2,screenHeight/2,Color.WHITE);
}
public void addNotify(){
super.addNotify();
startGame();
}
private void startGame(){
gameThread = new Thread(this);
gameThread.start();
}
@Override
public void run() {
while (!isGameOver) {
dbImage = createImage(screenWidth,screenHeight);
dbg = this.getGraphics();
if(!isPaused){
if(!gameOverCheck()){
updateGame();
paintComponents(dbg);
}
}else if(isPaused){
dbg.setColor(Color.ORANGE);
dbg.setFont(new Font("serif",Font.BOLD,50));
dbg.drawString("Paused", screenWidth/2-82, screenHeight/2);
}
try {
Thread.sleep(30);
} catch (InterruptedException e) {e.printStackTrace();}
}
}
private boolean gameOverCheck(){
if(player1.getScore() == playToPoints){
dbg.setColor(player1.getColour());
dbg.setFont(new Font("serif",Font.BOLD,50));
dbg.drawString("Player 1 Wins!", screenWidth/2 - 161, screenHeight/2);
setGameOver(true);
return true;
}else if(player2.getScore() == playToPoints){
dbg.setColor(player2.getColour());
dbg.setFont(new Font("serif",Font.BOLD,50));
dbg.drawString("Player 2 Wins!", screenWidth/2 - 161, screenHeight/2);
setGameOver(true);
return true;
}
return false;
}
private void updateGame(){
ball.move(screenWidth,screenHeight,player1,player2);
player1.aiForPadel(screenWidth, screenHeight, ball.getX(), ball.getY());
player2.aiForPadel(screenWidth, screenHeight, ball.getX(), ball.getY());
}
@Override
public void paintComponents(Graphics g) {
super.paintComponents(g);
dbg.setColor(Color.BLACK);
dbg.fillRect(0, 0, screenWidth+20, screenHeight+20);
dbg.setColor(Color.WHITE);
dbg.drawLine(screenWidth/2, 0, screenWidth/2, screenHeight);
dbg.setFont(new Font("serif",Font.BOLD,32));
dbg.drawString(player1.getScore()+"", screenWidth/2-40, screenHeight - 20);
dbg.drawString(player2.getScore()+"", screenWidth/2+20, screenHeight - 20);
ball.drawBall(dbg);
player1.drawPadel(dbg);
player2.drawPadel(dbg);
}
}
OriginalL'auteur user250643 | 2010-01-14
Vous devez vous connecter pour publier un commentaire.
Il y a un très bon tutoriel ici qui explique comment utiliser BufferStrategy pour produire de la non-scintillement de l'animation.
Les points importants sont:
setIgnoreRepaint(true)
sur le haut-niveauCanvas
pour empêcher l'AWT de repeindre, comme vous pouvez généralement le faire vous-même à l'intérieur de la boucle d'animation.Graphics2D
objet de laBufferStrategy
(plutôt que d'utiliser l'instance passée parpaintComponent(Graphics g)
.OriginalL'auteur Adamski
Un doit lire au sujet de la peinture mécanisme de AWT et Swing
La peinture dans AWT et Swing
Votre accueil ^^
Tandis que ceci peut théoriquement répondre à la question, il serait préférable pour inclure l'essentiel des éléments de réponse ici, et de fournir le lien de référence.
OriginalL'auteur helpermethod
Le problème de base est, vous êtes en violation de la peinture de base du système de Swing. Swing utilise un "passif rendu" de l'algorithme, où les peintures sont réalisées uniquement quand ils ont besoin de l'être. Vous pouvez faire des suggestions à l'API sur quand quelque chose doit être mise à jour via le
repaint
appel.Basé sur votre code, le problème de base est, vous êtes d'appel
paintComponents
avec votre propreGraphics
contexte, mais le système est alors complètement ravager, de peinture de peinture de passe, vous vous battez le système de peinture plutôt que de travailler avec elle.Si fait correctement, les composants Swing sont déjà double tampon, de sorte que vous n'avez pas besoin de faire quoi que ce soit "extra", d'autres, puis réelle de travail avec l'API/système.
Je fortement vous recommandons d'avoir un coup d'oeil à:
pour obtenir une meilleure compréhension de la façon dont les travaux de peinture dans les Swing.
Donc, nous allons commencer avec...
paint
méthode directement. Le système se chargera d'effectuer cette opération lorsque l'on souhaite mettre à jour votre composant.Je vous recommande fortement d'avoir une lecture de:
Par exemple...
BufferedStrategy
A déjà été suggéré,
BufferStrategy
est une solution viable dans le cas où vous voulez prendre le contrôle complet hors du système de peinture. C'est plus complexe, mais vous permet de vous autour de la bizarreries de l'passive système de rendu utilisé par SwingOriginalL'auteur MadProgrammer
Je pense que vous pouvez simplement appeler
super(true);
première chose, et elle dit juste la
JPanel
qu'il est double tampon... parce que l'un desJPanel
's les constructeurs est:J'espère que cela aide quelqu'un, même s'il est près de quatre ans plus tard.
OriginalL'auteur dylnmc