[Java] Interface graphique n'actualise pas l'affichage

Fermé
Max - 18 mai 2016 à 23:20
 Max - 19 mai 2016 à 00:43
Bonjour, voila mes 3 classes, je ne comprend pas pourquoi quand j'utilise les fleches directionnelles (et les println() me confirment que c'est détecté par le programme) la flèche affichée par paintComponent(Graphics g) ne se déplace pas latéralement:

public class main{
	public static void main(String[] args){
		Frame frame = new Frame();
	}
}


import javax.swing.*;
import java.awt.event.*;
import java.awt.*;
 
public class Frame extends JFrame implements KeyListener{

	
	private int frame_height = 700;
	private int frame_width = 1000;
	private Graphic graphic;

	public Frame(){
		super();
		addKeyListener(this);

		this.setTitle("Test");
		this.setSize(frame_width,frame_height);
		this.setLocationRelativeTo(null);
		this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		
		this.setVisible(true);
		graphic = new Graphic(this);
		this.setContentPane(graphic);
		this.getContentPane().setBackground(Color.RED);
	}


	public void keyTyped(KeyEvent e) {
	//Invoked when a key has been typed. 
	//This event occurs when a key press is followed by a key release.
	}

	public void keyPressed(KeyEvent e) {
		if(e.getKeyCode() == 37){
			graphic.moveLeft();
			System.out.println("Gauche");
		}

		if(e.getKeyCode() == 39){
			graphic.moveRight();
			System.out.println("Droite");
		}
		graphic.repaint();
		graphic.updateUI();
	}

	public void keyReleased(KeyEvent e) {
		
	}

	public int getHeight(){
		return this.frame_height;
	}

	public int getWidth(){
		return this.frame_width;
	}
}


import java.awt.*;
import javax.swing.*;

public class Graphic extends JPanel{ 
	private Frame frame;
	private int persoX[] = new int[3];
	private int persoY[] = new int[3];
	private int x = 0;
	private int speed = 5;

	public Graphic(Frame frame){
		super();
		this.frame = frame;
		persoX[0] =30+x;
		persoX[1] =50+x;
		persoX[2] =70+x;

		persoY[0] = this.frame.getHeight()-20;
		persoY[1] = this.frame.getHeight()-70;
		persoY[2] = this.frame.getHeight()-20;
	}

	public void paintComponent(Graphics panel){
		panel.fillPolygon(persoX, persoY, 3);
	}

	public void moveRight(){
		if(x<frame.getWidth()-speed-40){
			x = x+speed;
		}
	}

	public void moveLeft(){
		if(x>speed){
			x = x-speed;
		}
	}
}
A voir également:

1 réponse

KX Messages postés 16733 Date d'inscription samedi 31 mai 2008 Statut Modérateur Dernière intervention 31 janvier 2024 3 015
19 mai 2016 à 00:32
Bonjour,

Le problème vient du fait que moveLeft et moveRight modifient
x
qui n'est utilisée que lors du constructeur, alors que pour l'affichage tu utilises persoX qui lui n'ai jamais modifié par le curseur.

Remarques :

Je t'invite à ne pas faire de classes
extends JFrame implements KeyListener
, c'est une erreur de conception objet.

Autre problème de conception :
graphic = new Graphic(this);

Un composant n'a pas besoin d'avoir une référence de son conteneur puisqu'il connaît déjà cette information au travers de la méthode getParent()
En plus dans ton cas, tu regardes juste la taille du conteneur, alors que la taille du composant lui même pourrait te suffire.

Attention : getWidth et getHeight existent déjà pour une Frame et changer leur comportement comme tu l'as fait peut avoir des effets de oords catastrophique.

Voici une version modifiée de ton code, qui fonctionne, et avec quelques améliorations, en particulier au cas où la fenêtre serait redimensionnée.

import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;

import javax.swing.JFrame;

public class Frame extends JFrame {

    public Frame() {
        super("Test");

        Graphic graphic = new Graphic();
        addKeyListener(new KeyAdapter() {
            @Override
            public void keyPressed(KeyEvent e) {
                switch (e.getKeyCode()) {
                case KeyEvent.VK_LEFT:
                    graphic.moveLeft();
                    break;
                case KeyEvent.VK_RIGHT:
                    graphic.moveRight();
                    break;
                }
            }
        });

        setSize(1000, 700);
        setContentPane(graphic);
        setLocationRelativeTo(null);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        setVisible(true);
    }
}

import java.awt.Container;
import java.awt.Graphics;

public class Graphic extends Container {
    private int width = 40, height = 50;
    private int x = 0;
    private int speed = 5;

    @Override
    public void paint(Graphics g) {
        super.paint(g);
        x = Math.max(0, Math.min(x, getWidth() - width));
        int[] persoX = { x, x + width / 2, x + width },
              persoY = { getHeight(), getHeight() - height, getHeight() };
        g.fillPolygon(persoX, persoY, 3);
    }

    public void moveRight() {
        x += speed;
        repaint();
    }

    public void moveLeft() {
        x -= speed;
        repaint();
    }
}
0
Nickel, je test demain mais ca semble logique.
Merci :)
0