Aumentar o tamanho da janela fazendo com que as bolinhas se movam por todo o novo espaço

"Utilize os eventos do escutador ComponentListener no JogoPainel e lembre-se de modificar ALTUR E LAGURA tanto do painel quanto das bolinhas."
Pessoal preciso fazer isso o que está escrito no “assunto” e essa continuação acima, só que não entendi mt bem como é que eu vou fazer isso, o que eu sei é que tenho que usar os eventos do escutador do ComponentListener, mas não tenho uma ideia de como fazer isso.
Aqui está a classe…

import java.awt.*;  
import javax.swing.*;  
  
  
/** 
* @author Alisson A classe bola é um componente para ser pintada em qualquer 
*         janela. A bola controla sua posição e orientação em relação a janela 
*         que estiver sendo pintada. @Todo os direitos reservados 
*/  
  
public class Bola extends JPanel {  
      
    private int x = 50, y = 150, direcaoX = 1, direcaoY = 1, tamanho = 30, idade;  
    private int ALTURA = 460; // Limite da janela (igual do JogoPainel)  
    private int LARGURA = 500; // Limite da janela (igual do JogoPainel)  
    private Color cor = Color.BLUE; // Cores para a bolinha (WHITE, GREEN,  
                                        // BLACK, BLUE, RED)  
  
    /** 
     * O construtor da bola que recebe os parametros inicias da bola 
     *  
     * @param x 
     *            = Posição inicial no eixo x (cresce esquerda para direita) 
     * @param y 
     *            = Posição inicial no eixo y (cresce de cima para baixo) 
     * @param direcaoX 
     *            = (1 = para direita; -1 para esquerda) 
     * @param direcaoY 
     *            = (1 para baixo; -1 para cima) 
     *  
     */  
public Bola(int x, int y, int direcaoX, int direcaoY) {  
        super();  
  
        // Usando os metodos set para testar os limites dos valores  
        this.setX(x);  
        this.setY(y);  
        this.setDirecaoX(direcaoX);  
        this.setDirecaoY(direcaoY);  
    }  
  
    /** 
     * Construtor da bola que não faz nada e inicializa a bola com os valores 
     * padrão dados na inicialização das variáveis. 
     */  
public Bola() {}  
  
      
    /* funções utilizadas somente como teste nesse exemplo */  
    /* 
     * Pinta a bola na tela dada por g 
     */  
public void paintComponent(Graphics g) {  
        super.paintComponent(g); // Pinta o fundo da tela  
        g.setColor(cor); // Cor da bola  
        g.fillOval(x, y, tamanho, tamanho); // Pinta a bola nas posições x e y  
                                            // Com largura e altura.  
        g.setColor(Color.WHITE);  
        g.drawString(String.valueOf(idade),(direcaoX+x)+(tamanho/2),(direcaoY+y)+(tamanho/2));  
}  
  
  
    /** 
     * Define a movimentação da bola em relação a sua posição inicial x e y. 
     */  
public void moveBola() {  
        // Trata os limites da tela  
        if (x >= LARGURA - tamanho) {  
            idade++;  
            direcaoX = -1;  
        } else if (x <= 0) {  
            idade++;  
            direcaoX = 1;  
        }  
  
        if (y >= ALTURA - tamanho) {  
            idade++;  
            direcaoY = -1;  
        } else if (y <= 0) {  
            idade++;  
            direcaoY = 1;  
        }  
        x += direcaoX; // Acrescenta 1 ou -1 conforme valor da direção  
        y += direcaoY; // Acrescenta 1 ou -1 conforme valor da direção  
    }  
  
    // ----------------------------- METODOS get e  
    // set----------------------------//  
    /** 
     * @return the x 
     */  
    public int getX() {  
        return x;  
    }  
  
    /** 
     * @param x 
     *            the x to set 
     */  
    public void setX(int x) {  
        if (x < LARGURA + tamanho) {  
            this.x = x;  
        }  
    }  
  
    /** 
     * @return the y 
     */  
    public int getY() {  
        return y;  
    }  
  
    /** 
     * @param y 
     *            the y to set 
     */  
    public void setY(int y) {  
        if (y < ALTURA + tamanho) {  
            this.y = y;  
        }  
    }  
  
    /** 
     * @return the direcaoX 
     */  
    public int getDirecaoX() {  
        return direcaoX;  
    }  
  
    /** 
     * @param direcaoX 
     *            the direcaoX to set 
     */  
    public void setDirecaoX(int direcaoX) {  
        if ((direcaoX == 1) || (direcaoX == -1)) { // '||' == 'ou' == 'or'. '&&'  
                                                    // == 'e' == 'and'  
            this.direcaoX = direcaoX;  
        }  
    }  
  
    /** 
     * @return the direcaoY 
     */  
    public int getDirecaoY() {  
        return direcaoY;  
    }  
  
    /** 
     * @param direcaoY 
     *            the direcaoY to set 
     */  
    public void setDirecaoY(int direcaoY) {  
        if ((direcaoX == 1) || (direcaoX == -1)) {  
            this.direcaoY = direcaoY;  
        }  
    }  
  
    /** 
     * @return the tamanho 
     */  
    public int getTamanho() {  
        return tamanho;  
    }  
  
    /** 
     * @param tamanho 
     *            the tamanho to set 
     */  
    public void setTamanho(int tamanho) {  
        if ((tamanho < ALTURA) && (tamanho < LARGURA)) {  
            this.tamanho = tamanho;  
        }  
    }  
  
    /** 
     * @return the aLTURA 
     */  
    public int getALTURA() {  
        return ALTURA;  
    }  
  
    /** 
     * @param aLTURA 
     *            the aLTURA to set 
     */  
    public void setALTURA(int aLTURA) {  
        ALTURA = aLTURA;  
    }  
  
    /** 
     * @return the lARGURA 
     */  
    public int getLARGURA() {  
        return LARGURA;  
    }  
  
    /** 
     * @param lARGURA 
     *            the lARGURA to set 
     */  
    public void setLARGURA(int lARGURA) {  
        LARGURA = lARGURA;  
    }  
  
    /** 
     * @return the cor 
     */  
    public Color getCor() {  
        return cor;  
    }  
  
    /** 
     * @param cor 
     *            the cor to set 
     */  
    public void setCor(Color cor) {  
        this.cor = cor;  
    }  
    public int getIdade(){  
        return idade;  
    }  
    // ---------------------------FIM-METODOS get e  
    // set--------------------------//  
  
}  

E aqui a classe JogoPainel…

import java.awt.*;  
import javax.swing.*;  
import java.awt.event.*;  
import java.util.ArrayList;  
import java.util.List;  
  
/** 
* @author Alisson Classe que desenha a janela do jogo. Necessária para pintar 
*         os objetos que serão acrescentados na janela. @Todos os direitos reservados 
*  
*/  
public class JogoPainel extends JPanel implements Runnable {  //Implements ActionListener     
      
    ArrayList<Bola> lista = new ArrayList<Bola>(); //Array pra criar várias bolinhas   
    Bola bola = new Bola();// Cria a bola  
    public JButton botao,button; //  
    public JTextField campo; //  
    private static final int LARGURA = 500; // Largura da janela  
    private static final int ALTURA = 500; // Altura da janela  
    private Thread animacao; // Controla a chamada de run  
    private int tempoEspera = 12; // Tempo entre uma pintura da tela e outra  
    private boolean rodando = true; // Define se está ou não rodando  
      
public JogoPainel() {  
        setBackground(Color.BLACK);  
        setLayout(new BorderLayout());  
        setPreferredSize(new Dimension(LARGURA, ALTURA));  
        campo = new JTextField(5);  
        botao = new JButton("Play/Pause"); //Cria um botao @2B  
        botao.addActionListener(new ActionListener(){ //Dá ação ao botão @2B  
  
public void actionPerformed(ActionEvent e){  
    // Determina que quando pressionado o botao, ele executará uma ação (pausando e rodando as bolinhas)  
    if(rodando){    
        rodando=false;   
    }else {   
        rodando=true;  
    }  
}  
});  
//botao que cria "x" bolinhas  
    button = new JButton("Insert");  
    button.addActionListener(new ActionListener(){  
public void actionPerformed(ActionEvent e){  
    Integer criadorBola = Integer.parseInt(campo.getText()); //implementação do botão ao textField  
    criadorBola = criadorBola -1;  
    for(int i=0;i<=criadorBola;i++){  
        lista.add(criaBola());                    
    }  
}  
});  
  
//Adiciona os botoes ao painel  
JLabel txt = new JLabel("Quantas bolinhas você deseja inserir ?"); //Cria um label @2B  
JPanel painel = new JPanel(); //Cria um painel @author 2B  
painel.add(txt, BorderLayout.SOUTH);   
painel.add(campo, BorderLayout.SOUTH);  
painel.add(button, BorderLayout.SOUTH);  
painel.add(botao, BorderLayout.SOUTH);//Adiciona o botao ao painel na parte Sul da tela @2B  
add(painel, BorderLayout.SOUTH); //Adiciona o painel na parte Sul da tela @2B  
}  
private Bola criaBola() {  
        Bola bolinhas;  
        // posiçoes iniciais x,y das bolinhas criadas aleotariamentes  
        int x = (int)(Math.random()*420);  
        int y = (int)(Math.random()*420);  
        int ex;  
        int cy;  
        if(x%3 ==1){  
             ex = 1;  
            }else{ex = 2;}  
        if(y%3 ==1){  
            cy = 1;  
            }else{cy = 2;}  
          
        bolinhas = new Bola(x,y,ex,cy);  
        return bolinhas;  
    }     
    /* 
     * Quando a janela aparece (addNotify) chama iniciarJogo 
     */  
public void addNotify() {  
        super.addNotify();  
        iniciarJogo();  
    }  
  
private void iniciarJogo() {  
        if (animacao == null || !rodando) {  
            animacao = new Thread(this);  
            animacao.start();  
  
        }  
    }  
  
    /* 
     * Roda a animação da bola 
     */  
public void run() {  
  
        while (true) { // loop do jogo para sempre  
            if (rodando) {  
                for (Bola bola : lista) {     
                    if(bola.getIdade()>=30){  
                          
                    }  
                    bola.moveBola(); // Chama para mover a bola  
                }         
                    repaint(); // Pede para repitar a bola  
            }  
                    try { // Inicia o tratamento de evento(erro)  
                    Thread.sleep(tempoEspera);  
                } catch (InterruptedException e) {  
                    e.printStackTrace();  
                }  
        }  
    }  
      
  
    /* 
     * Pinta a tela (super) e os componentes (bolas) 
     */  
public void paintComponent(Graphics g) {  
        super.paintComponent(g); // Repinta a tela  
        for (Bola bola: lista){  
        bola.paintComponent(g); // Repinta os componentes  
          
    }  
}  
public static void main(String args[]) {  
        JogoPainel jogoPainel = new JogoPainel(); // Cria a janela JogoPainel;  
        JFrame jogo = new JFrame("Grupo 1 - 2B Informática"); // Cria a moldura  
        jogo.add(jogoPainel); // Adicina a moldura jogo a janela jogoPainel  
        jogo.pack(); // Alinha a janela na moldura  
        jogo.setVisible(true); // Torna a janela visível.  
        // Fecha o programa ao clicar no x da janela  
        jogo.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);  
    }  
}  

Quando a tela for redimensionada, você precisa atualizar os campos LARGURA e ALTURA da classe Bola usando os métodos setLARGURA() e setALTURA(). Eles estão fixos em 500 e 460, por isso as bolinhas não ocupam a tela inteira.

Abraço.