Necesito ayuda para arreglar mi juego. He hecho todo lo posible para activar el doble buffer y evitar parpadeos, pero no es suficiente. Las imágenes estáticas quedan perfectas, sin embargo cuando algo se mueve en la pantalla empieza a parpadear como si se estuviera dibujando a la vez en dos posiciones distintas.
El parpadeo solo aparece en Linux, en Windows funciona bien. Necesito que funcione en Linux y ya no sé qué hacer. Os agradecería mucho que probarais el programa y me dierais alguna idea.
ESTA ES LA CLASE DE LA VENTANA
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class clsWindow extends JFrame implements WindowListener{
clsPanel panel;
public clsWindow(){
addWindowListener(this);
setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOS E);
panel = new clsPanel();
setContentPane(panel);
setTitle("Flickering example");
setResizable(false);
setSize(800, 600);
setVisible(true);
}
public void addNotify(){
super.addNotify();
setResizable(false);
Insets insets = getInsets();
setSize(
(int) Math.round(800 + insets.left + insets.right),
(int) Math.round(600 + insets.top + insets.bottom)
);
setLocationRelativeTo(null);
this.getContentPane().requestFocusInWindow();
}
public void windowOpened (WindowEvent e){}
public void windowActivated (WindowEvent e){this.getContentPane().requestFocusInWindow();}
public void windowDeactivated(WindowEvent e){}
public void windowIconified (WindowEvent e){}
public void windowDeiconified(WindowEvent e){this.getContentPane().requestFocusInWindow();}
public void windowClosing (WindowEvent e){
if(panel != null){panel.stopAnimation();} // Stop animation thread
dispose();
System.exit(0);
}
public void windowClosed (WindowEvent e){}
}
ESTA ES LA CLASE DEL PANEL
import java.awt.*;
import javax.swing.*;
public class clsPanel extends JPanel implements Runnable{
private int Xposition, increment;
private boolean direction;
private static final int TEMPORAL_RESOLUTION = 10; // milliseconds
// Frame duration. Chosen value must be multiple of temporal resolution.
// 40 ms 25 fps
// 35 ms 28,5 fps
// 30 ms 33,3 fps
// 25 ms 40 fps
// 20 ms 50 fps
// 15 ms 66,6 fps
private static final float FRAME_DURATION = 20; // ms
private Thread animationThread;
private volatile boolean running; // This variable is shared with the event dispatch thread
public clsPanel(){
this.setIgnoreRepaint(true);
increment = 2;
direction = true;
}
public void addNotify(){
super.addNotify();
setDoubleBuffered(true);
running = true;
animationThread = new Thread(this);
animationThread.start();
}
public void stopAnimation(){running = false;}
public void run() {
long loopDuration = 0, previous = 0, delay = 0, aux = 0, interim = 0, correction = 0;
int lastFrame = 0;
// Main loop
previous = 0;
while (running){
motion(); // move the square
if(lastFrame == FRAME_DURATION){lastFrame = 0; repaint();} // Repaint
aux = System.nanoTime();
if(previous == 0){
correction = 0;
loopDuration = (TEMPORAL_RESOLUTION * 1000000);
}else{
loopDuration = aux - previous;
correction = loopDuration - (TEMPORAL_RESOLUTION * 1000000);
}
previous = aux;
delay = correction;
do{
try {Thread.sleep(1);} catch (InterruptedException e) {};
interim = System.nanoTime() - aux;
delay = delay + interim;
aux = System.nanoTime();
} while(delay < (TEMPORAL_RESOLUTION - 1) * 1000000);
lastFrame += TEMPORAL_RESOLUTION;
}
}
private void motion(){
if(direction == true){
if(Xposition < 700){
Xposition += increment;
}else{
direction = false;
}
}else{
if(Xposition > 0){
Xposition -= increment;
}else{
direction = true;
}
}
}
public void paintComponent(Graphics g){
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASI NG, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_TEXT_ANTIA LIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
// Background
g2d.setColor(Color.decode("0xe0e0e0"));
g2d.fillRect(0, 0, 800, 600);
// Square
g2d.setColor(Color.decode("0x202020"));
g2d.fillRect((int) Math.round(Xposition), 250, 100, 100);
g2d.dispose();
Toolkit.getDefaultToolkit().sync();
}
}