0

I'm coding a JApplet in Java, but dubble buffering doesn't remove the flickering!?

What should I do?

This is the important part of the code, I guess (tell me if you need to know more, please):

    // Background (dubble buffering)
    private Image backbuffer;
    private Graphics backg;

//Init method
            // Dubble-Buffering
        backbuffer = createImage(getWidth(), getHeight());
        backg = backbuffer.getGraphics();
        backg.setColor(this.getBackground());

//Overrided update method
       public void update( Graphics g ) {
          g.drawImage( backbuffer, 0, 0, this );
          getToolkit().sync();
       }

I appreciate all help I can get! :)

Casper Lindberg
  • 1,053
  • 1
  • 11
  • 16
  • `Swing` is [double buffered by default](http://docs.oracle.com/javase/tutorial/extra/fullscreen/doublebuf.html), IMHO. Why you using `update()` method manually? What prompted this decision of yours? Some idea about what you were trying to accomplish, will be of great help, as to what you thought, and what exactly didn't worked out or in what way? – nIcE cOw Jun 17 '14 at 15:47
  • A small quote from `Java Docs Container` Class states: __"Updates the container. This forwards the update to any lightweight components that are children of this container. If this method is reimplemented, super.update(g) should be called so that lightweight components are properly rendered, or directly call paint(g). If a child component is entirely clipped by the current clipping setting in g, update() will not be forwarded to that child."__ – nIcE cOw Jun 17 '14 at 15:50
  • I'm sorry, but I'm quite new to game programming in Java so I just tried something to fix the problem. Obviously you are right as it doesn't work at all, but how should I fix the flickering then? Do you need to see all the code? – Casper Lindberg Jun 17 '14 at 18:11
  • If you use a `JPanel` to draw on, instead of directly drawing on a `JApplet` then it will be easy. Please have a look at this [example](http://stackoverflow.com/a/13795187/1057230). Just a simple starting point. – nIcE cOw Jun 17 '14 at 22:18
  • For better help sooner, post an [MCVE](http://stackoverflow.com/help/mcve) (Minimal Complete and Verifiable Example). – Andrew Thompson Jun 18 '14 at 09:22

1 Answers1

0

I made an MCVE to give you a better insight of the problem (thanks to Andrew Thompson)!

"Main"-class:

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JApplet;
import javax.swing.JButton;
import javax.swing.Timer;

public class Test extends JApplet implements ActionListener {

JButton start;

int delay;
Timer tm;

// Falling balls
int n; // Total balls
Ball[] ball; // Array with the balls in

int score;

// The amount of balls falling at the same time (increases by one every
// 10:th score)
int ballNr;

// Comment to the game
String comment;

public void init() {

    this.setLayout(null);
    this.setSize(600, 500);
    this.getContentPane().setBackground(Color.cyan);
    this.setFocusable(true);

    score = 0;
    ballNr = 3;
    comment = "Avoid the balls!";

    // Buttons
    start = new JButton("START");
    add(start);
    start.setBounds(0, 400, 200, 100);
    start.addActionListener(this);

    // The timer
    delay = 12;
    tm = new Timer(delay, this);

    // The falling balls
    n = 12; // Number of balls in total
    ball = new Ball[n];
    // Declaring twelve new instances of the ball-object with a
    // "reference array"
    for (int i = 0; i < n; i++) {
        ball[i] = new Ball();
    }
}

// Paint-method //
public void paint(Graphics g) {
    super.paint(g);

    // Every 10:th score, the game adds one ball until you reach 100 =
    // win! (ballNr + (int)(score * 0.1) -> ballNr increases by one
    // every 10:th score
    for (int i = 0; i < ballNr + (int) (score * 0.1); i++) {
        // Score can't be higher than 100
        if (score < 100) {
            g.setColor(ball[i].getCol());
            g.fillOval(ball[i].getXLoc(), ball[i].getYLoc(),
                    ball[i].getSize(), ball[i].getSize());
        }
    }

    // Draw the score and the comment
    g.setColor(Color.black);
    g.setFont(new Font("Arial", Font.BOLD, 24));
    g.drawString("SCORE: " + score, 440, 40);

    g.setColor(Color.red);
    g.setFont(new Font("Arial", Font.BOLD + Font.ITALIC, 28));
    g.drawString(comment, 0, 40);

}

// ACTIONLISTENER //
public void actionPerformed(ActionEvent e) {

    if (e.getSource() == start) {
        tm.start();
        this.requestFocusInWindow(); // Make the runner component have focus
    }

    // Every 10:th score, the game adds one ball until you reach 100 =
    // win! (ballNr + (int)(score * 0.1) -> ballNr increases by one
    // every 10:th score
    for (int i = 0; i < ballNr + (int) (score * 0.1); i++) {
        // Score can't pass 100, because then you have won the game
        if (score < 100) {
            ball[i].setYLoc(ball[i].getYLoc() + ball[i].getVel());
        }
    }

    // If any ball is out of bounds (then the score increases by one)
    for (int i = 0; i < n; i++) {
        if (outOfBounds(ball[i])) {
            ball[i] = new Ball();
        }
    }
    repaint();
}

// If the ball is out of the screen
public boolean outOfBounds(Ball ball) {
    if (ball.getYLoc() >= 500) {
        score++;
        return true;
    } else {
        return false;
    }
}

// Updates new balls
public void updateBalls() {
    for (int i = 0; i < n; i++) {
        ball[i] = new Ball();
    }
}
}

Sub-class

import java.awt.Color;
import java.util.Random;

public class Ball {
// Private variables
private Random r; // Generating random positions and
                    // sizes;
private int size; // Size of the ball
private int vel; // Ball velocity
private int nrOfCol; // Color code (see ballColor-method)
private Color col;
private int xLoc;
private int yLoc;

// Constructor
public Ball() {
    r = new Random();
    size = r.nextInt(40) + 10; // 10px - 50 px
    vel = r.nextInt(6) + 1; // Speed btw 1-5 px/delay
    nrOfCol = r.nextInt(8) + 1; // Specific nr from 1-9
    col = ballColor();
    xLoc = r.nextInt(550);
    yLoc = 0;}

public Ball(int xPos, int yPos, int size, int vel, Color col) {
    this.xLoc = xPos;
    this.yLoc = yPos;
    this.size = size;
    this.vel = vel;
    this.col = col;
}

// A method to generate different colors of the balls
public Color ballColor() {
    Color col;
    switch (nrOfCol) {
    case 1:
        col = Color.black;
        break;
    case 2:
        col = Color.red;
        break;
    case 3:
        col = Color.green;
        break;
    case 4:
        col = Color.yellow;
        break;
    case 5:
        col = Color.pink;
        break;
    case 6:
        col = Color.magenta;
        break;
    case 7:
        col = Color.white;
        break;
    case 8:
        col = Color.orange;
        break;
    case 9:
        col = Color.blue;
        break;
    default:
        col = Color.black;
        // All colors except cyan as it is the background color
    }
    return col;
}

// Getters & setters

public int getXLoc() {
    return xLoc;
}

public int getYLoc() {
    return yLoc;
}

public void setYLoc(int y) {
    yLoc = y;
}

public int getSize() {
    return size;
}

public int getVel() {
    return vel;
}

public Color getCol() {
    return col;
}
}
Casper Lindberg
  • 1,053
  • 1
  • 11
  • 16