Afficher une image en arrière plan dans un jpanel

Soyez le premier à donner votre avis sur cette source.

Vue 14 245 fois - Téléchargée 1 958 fois

Description

Cette classe permet de créer un JPanel qui contient en arrière plan une image. La taille de l'image s'adapte automatiquement à la taille du JPanel.

Source / Exemple :


package fr.julien.panelimage;

import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.RenderingHints;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;
import javax.swing.JPanel;

/**
 * <b>PanelImage est la classe qui permet de définir un panel sur lequel on peut afficher une image en arrière plan</b>
 * <p>
 * Cette classe est caractérisée par les informations suivantes :
 * <ul>
 * <li>L'image à afficher dans le Panel</li>
 * </ul>
 * </p>
 * <p>
 * De plus, cette classe définit des méthodes permettant d'accéder à l'image en arrière plan et de la modifier.
 * </p>
 * <p>
 * Cette classe hérite de JPanel, il est donc possible d'utiliser toutes les méthodes de cette classe. En
 * particulier, on peut ajouter des composants au premier plans (par dessus l'image).
 * </p>
 * <p>
 * L'image qui est affichée en arrière plan est toujours maximisée dans le JPanel. Pour définir
 * la taille de l'image, on peut fixer la taille du JPanel grâce à la méthode setBounds() ou bien
 * en utilisant des layout.
 * </p>
 * 
 * @author Julien
 * @version 1.0
 *
 */
public class PanelImage extends JPanel {

    /**
     * L'identifiant de sérialisation
     */
    private static final long serialVersionUID = -6350324456764768311L;

    private Image image;

    /**
     * <b>Constructeur de PanelImage</b>
     */
    public PanelImage() {
        super();
    }
    
    /**
     * <b>Constructeur de PanelImage</b>
     * @param image
     *     L'image à afficher en arrière plan
     */
    public PanelImage(Image image) {
        super();
        setImage(image);
    }

    /**
     * <b>Constructeur de PanelImage</b>
     * @param path
     *     Le chemin de l'image à afficher en arrière plan
     * @throws IOException si le chemin n'est pas trouvé
     */
    public PanelImage(String path) throws IOException {
        super();
        setImage(path);
    }
    
    /**
     * Méthode qui permet de modifier l'image
     * @param image
     *     La nouvelle image à afficher
     */
    public void setImage(Image image) {
        this.image = image;
        repaint();
    }
    
    /**
     * Méthode qui permet de modifier l'image
     * @param path
     *     Le chemin vers la nouvelle image à afficher
     * @throws IOException si le chemin n'est pas trouvé
     */
    public void setImage(String path) throws IOException {
        try {
            this.image = ImageIO.read(new File(path));
            repaint();
        } 
        catch (IOException e) {
            throw new IOException(path+" introuvable", e);
        }
    }

    /**
     * Méthode d'accès à l'image courante
     * @return l'image affichée en arrière plan
     */
    public Image getImage() {
        return image;
    }
    
    @Override
    public void paintComponent(Graphics g){
        if(image!=null){
            Graphics2D g2d = (Graphics2D)g;
            g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
            g2d.drawImage(image, 0, 0, getWidth(), getHeight(), null);
        }
    }

}

Codes Sources

A voir également

Ajouter un commentaire

Commentaires

uhrand
Messages postés
493
Date d'inscription
samedi 20 mai 2006
Statut
Membre
Dernière intervention
15 juillet 2012
7 -
C'est vrai que beaucoup de gens veulent savoir comment ajouter une image de fond à une fenêtre. La façon facile est d'ajouter une image à un JLabel, puis ajouter le JLabel à la fenêtre. Le code de cette approche facile serait quelque chose comme ceci:

JLabel contents = new JLabel ();
contents.setIcon (image);
contents.setLayout (new BorderLayout ());
frame.add(contents);

Pourquoi ceci fonctionne? Eh bien, rappelez-vous que tous les composants Swing hérites de la classe "Container", de sorte que vous pouvez ajouter des composants enfants. Toutefois, par défaut, un JLabel utilise une disposition nulle et les composants n'apparaissent pas. En utilisant un BorderLayout, le JLabel peut maintenant fonctionner comme un JPanel et être utilisé comme un volet de contenu.

Cependant, cette approche présente des inconvénients, surtout parce qu'un JLabel peint l'image à sa taille réelle. Donc, en réalité, elle ne serait probablement utilisée uniquement sur les fenêtres de taille fixe, où la taille de la fenêtre est déterminée par la taille de l'image.

Dans la plupart des autres cas, nous devons adopter une approche plus flexible, donc nous avons besoin d'un composant plus souple. PanelImage, présentée ici par notre cher ami Julien39, est une extension de JPanel qui permet aux images d'être peint à l'échelle.

BackgroundPanel est également une extension de JPanel:
http://www.camick.com/java/source/BackgroundPanel.java
Le support de base fourni par cette classe permet aux images d'être peint dans l'un des trois styles suivants:

* L'image à l'échelle (la valeur par défaut)
* Les images en mosaïque
* L'image à la taille réelle - la position de l'image est contrôlé en précisant l'alignement horizontal et vertical (l'alignement au centre est la valeur par défaut)

En plus de dessiner des images, ce composant peut également être utilisé pour les fonds qui ne sont pas une couleur unie. L'API Java fournit une interface "Paint" très commode. Une nouvelle méthode setPaint (...) a été ajouté pour spécifier un objet "Paint" pour être utilisé par le code de peinture personnalisée. L'objet "Paint" peut être utilisé sans une image. Lorsqu'à la fois une image et un objet "Paint" sont utilisés, l'ordre de la peinture sera:

* Peindre le fond
* Peindre à l'aide de l'objet Paint
* Dessiner l'image

En outre, les méthodes add(...) ont été substituées pour rendre non-opaque chaque composant ajouté au panneau. Après tout, si vous vous faites la peine de créer un beau fond de fantaisie, vous ne voulez pas qu'un composant opaque bloque la peinture personnalisée. Pour les composants qui utilisent un "renderer", le "renderer" devra également faire preuve de transparence. Par exemple, sur une JTable, vous pouvez utiliser le code suivant pour définir la valeur alpha de la couleur à 0, ce qui se traduit par une couleur de fond transparente:

table.setBackground( new Color(0, 0, 0, 0) );

Pour finir, voici encore un exemple de code utilisé pour créer un panneau qui utilise à la fois une image et un objet Paint:

BackgroundPanel panel = new BackgroundPanel(image, BackgroundPanel.ACTUAL, 1.0f, 0.5f);
GradientPaint paint = new GradientPaint(0, 0, Color.BLUE, 600, 0, Color.RED);
panel.setPaint(paint);
KX
Messages postés
16028
Date d'inscription
samedi 31 mai 2008
Statut
Modérateur
Dernière intervention
18 septembre 2019
88 -
Une suggestion d'amélioration, pour permettre de charger une image à l'intérieur d'un JAR :

/**
 * Change l'image à afficher.<br>
 * L'image est d'abord cherchée à l'intérieur du classpath (le JAR s'il existe)<br>
 * Si elle n'a pas été trouvée, elle est cherchée dans le système de fichiers.
 * @param path le chemin d'accès à la nouvelle image
 * @throws IOException si l'image n'est pas chargée
 */
public void setImage(String path) throws IOException
{
    try
    {
        URL inJar = getClass().getClassLoader().getResource(path);
        
        if (inJar != null)
            image = ImageIO.read(inJar);
        else
            image = ImageIO.read(new File(path));
    } 
    catch (Exception e)
    {
        throw new IOException("unloadable: "+path, e);
    }
        
    repaint();
}

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.