Welcome to Bukkit France

Inscrivez-vous maintenant pour profiter d'un accès total à tout le contenu offert par la meilleur communauté Bukkit française ! Une fois inscrit et connecté, vous pourrez contribuez à la communauté en postant vos propres sujets et questions ou en répondant à ceux existants. Vous pourrez aussi customiser votre profil, recevoir des points de réputations, communiquer avec les autres membres via le chat, et plus encore! 

  • Annonces

    • Pskyco

      Bukkit France passe sous Discord !   02/20/16

      Bukkit France est désormais passé sur Discord, au revoir donc notre vieux Teamspeak ! Téléchargez le client et venez nous rejoindre sur notre salon en suivant les instructions suivantes.
      M-à-j du 25/02/2017 : Désormais, seuls les comptes actifs sur le forum se verront donner l'accès au Discord, ce dernier n'est pas une plateforme d'aide de la même manière que le chat.
  • billets
    47
  • commentaires
    40
  • vues
    31701

Chapitre 34: Les boites de dialogue

SystemGlitch

1219 vues

blog-0400991001439390756.png

Vous les connaissez, il s'agit de ces petites fenêtres servant à afficher une information comme un avertissement ou une erreur, à demander une validation du style "Voulez-vous vraiment quitter? -> Oui / Non" ou encore demander une information à l'utilisateur.

En Java, elles portent le nom de JDialog tout simplement! Le JDK vous en propose déjà plusieurs toutes prêtes, ce qui est très pratique, mais si jamais vous avez besoin d'une boite de dialogue plus spécifique, il faudra alors la faire vous-même! N'ayez crainte, rien de bien difficile, c'est la même chose que pour les JFrame à une ou deux différences près.

 

Première différence: le reste du programme est figé tant que la boite de dialogue n'est pas fermée, à moins d'utiliser un Thread à part, mais nous n'avons pas encore vu comment faire.

Seconde différence: il est possible de rendre les JDialog modales, c'est à dire que tant qu'elles seront ouvertes, on ne pourra rien faire d'autre sur le logiciel que d’interagir avec la boite de dialogue. Vous en avez aussi rencontré j'en suis sûr.

 

Commençons par la partie la plus simple : les boites de dialogue informatives. Attention, pour les dialogs préfabriquées on utilisera JOptionPane et non pas JDialog ! Nous allons ajouter trois boutons à notre content pane, chacun ouvrira une boite de dialogue différente. Ces dernières sont modales, ce qui vous permettra de vous faire d'ores et déjà un idée de ce que cela signifie.

 
JButton info = new JButton("Ouvrir boite d'information");
info.addActionListener(new ActionListener() {

	@Override
	public void actionPerformed(ActionEvent arg0) {
		JOptionPane.showMessageDialog(null, "Message d'information", "Information", JOptionPane.INFORMATION_MESSAGE); //message d'information
	}
});

JButton warn = new JButton("Ouvrir boite d'avertissement");
warn.addActionListener(new ActionListener() {

	@Override
	public void actionPerformed(ActionEvent arg0) {
		JOptionPane.showMessageDialog(null, "Message préventif", "Attention", JOptionPane.WARNING_MESSAGE); //Message d'avertissement
	}

});

JButton err = new JButton("Ouvrir boite d'information");
err.addActionListener(new ActionListener() {

	@Override
	public void actionPerformed(ActionEvent arg0) {
		JOptionPane.showMessageDialog(null, "Message d'erreur", "Erreur", JOptionPane.ERROR_MESSAGE); //Message d'erreur
	}

});

 

kiF8YQb.pngYSZhJgv.pngQHrE7Sy.png

 

Revenons plus en détails sur la méthode que j'ai utilisé :

JOptionPane.showMessageDialog(null, "Message d'information", "Information", JOptionPane.INFORMATION_MESSAGE);

 

Le premier argument est le JComponent parent. C'est à dire le composant au dessus du quel devra s'ouvrir la fenêtre. S'il y en a pas comme ici, on met null. On aurait cependant pu mettre this pour centrer la boite de dialogue au dessus du content pane, même si la fenêtre principale avait été déplacée.

Le second argument est le message que l'utilisateur verra dans la boite de dialogue.

Le troisième est le titre de la boite de dialogue, affiché dans la barre d'action.

Et le dernier est celui qui définira s'il s'agit d'un message d'information, d'erreur ou d'avertissement. D'ailleurs il est possible de simplement mettre un message, sans icône, à l'aide de JOptionPane.PLAIN_MESSAGE, ou alors une question avec JOptionPane.QUESTION_MESSAGE.

 

Cette méthode est surchargée. Voyons un peu ce que l'on peut faire de plus ! :) Nous avons deux surcharges à notre disposition, l'une rajoute un argument de type ImageIcon, qui nous permettra donc de changer l'icône, l'autre permet de créer un boite de dialogue la plus simple qui soit car seuls les deux premiers arguments sont conservés.

 

Voici comment changer l'icône qui sera affichée :

ImageIcon img = new ImageIcon("check.png");
JOptionPane.showMessageDialog(null, "Sauvegarde réussie!", "Succès", JOptionPane.INFORMATION_MESSAGE , img);

 

4BPvWff.png

 

Jetons maintenant un œil aux boites de confirmation. Cette fois la méthode utilisée sera showConfirmDialog(). La différence c'est que celle-ci retourne un int indiquant le choix de l'utilisateur. Vous verrez ce sera tout de suite plus clair en voyant le code :

int option =JOptionPane.showConfirmDialog(null, "Êtes-vous sûr de vouloir quitter?", "Vraiment?" , JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE); //Vous pouvez encore changer l'icône en ajoutant une argument du type ImageIcon
if(option == JOptionPane.YES_OPTION)
	System.out.println("Quitter");
else if(option == JOptionPane.NO_OPTION)
	System.out.println("Ne pas quitter");

 

tDbYkvK.png

 
 
int option =JOptionPane.showConfirmDialog(null, "Le fichier est introuvable, continuer?", "Fichier introuvable" , JOptionPane.YES_NO_CANCEL_OPTION, JOptionPane.WARNING_MESSAGE);
if(option == JOptionPane.YES_OPTION)
	System.out.println("Continuer");
else if(option == JOptionPane.NO_OPTION)
	System.out.println("Ne pas continuer");
else if(option == JOptionPane.CANCEL_OPTION)
	System.out.println("Annuler");
else if(option == JOptionPane.CLOSED_OPTION) //L'utilisateur a fermé la boite de dialogue sans passer par les boutons "Oui" "Non" ou "Annuler"
        System.out.println("Fermer");

 

eDGwsly.png

 

Le principe est acquis, on passe à la suite! En effet ici on stockait une int renvoyée par la méthode, mais si on faisait une boite de dialogue qui demande à l'utilisateur d'écrire une chaine de caractères? Et bien c'est pareil! Sauf qu'on aura une String en retour :

String answer = JOptionPane.showInputDialog(null, "Comment vous appelez-vous?", "Vos identifiants" , JOptionPane.QUESTION_MESSAGE);
System.out.println("L'utilisateur s'appelle \""+ answer + "\".");

 

W60Bb0P.png

 

 

Allons un peu plus loin et proposons différents choix via un menu déroulant. On créera un tableau contenant les valeurs possibles et le donnera en argument :

String[] sex = { "Homme" , "Femme" , "Autre" };
String answer = (String) JOptionPane.showInputDialog(null, "Veuillez indiquer votre sexe.", "Vos identifiants" , JOptionPane.QUESTION_MESSAGE , null , sex , sex[0]);
System.out.println("Sexe de l'utilisateur: " + answer);

 

AlhcOuR.png

 

Le dernier argument est celui qui sera sélectionné par défaut dans le menu déroulant. Attention si l'utilisateur ferme la boite de dialogue autrement qu'en appuyant sur "OK", la valeur retournée sera null, et cela est aussi valable pour le champ de saisie vu juste au dessus! Il faudra donc bien vérifier vos résultats! Quand à l'argument null donné dans la méthode, il s'agit de l'icône modifiée. On ne souhaite pas la changer donc on donne null. ^_^

 

Voici la dernière variante de boite de dialogue préfabriquée: c'est le même principe que celle que nous venons de voir mais cette fois il y aura plusieurs boutons et non pas un menu déroulant.

String[] sex = { "Homme" , "Femme" , "Autre" };
int answer = JOptionPane.showOptionDialog(null, "Veuillez indiquer votre sexe.", "Vos identifiants" , JOptionPane.YES_NO_CANCEL_OPTION , JOptionPane.QUESTION_MESSAGE, null , sex , sex[0]);
//answer est le numéro du bouton qui a été cliqué par l'utilisateur, -1 si la fenêtre à été fermée par un autre moyen
//Vous pouvez donc mettre plus ou moins de trois boutons
if(answer >= 0)
	System.out.println("Sexe de l'utilisateur: " + sex[answer]);

 

14EDh1L.png

 

Bien, vous avez déjà de quoi faire. Mais certains cas ne sont pas gérés, ou alors, vous souhaitez simplement faire un boite de dialogue ayant un style visuel bien particulier. Vous savez déjà faire tout ça! Le procédé est exactement le même que pour la création d'une JFrame, sauf que votre classe héritera de JDialog. ;)

Votre code cadeau sera une boite de dialogue d'erreur faite maison! Pensez à l'utiliser avec le code cadeau donné dans le chapitre sur les exceptions ! :)

package fr.bukkit.jeremgamer.cours;

import java.awt.BorderLayout;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Toolkit;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.StringSelection;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;

import javax.swing.Box;
import javax.swing.Icon;
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.UIManager;

public class CustomDialog extends JDialog {

    private JLabel message = new JLabel("<html><b>Une erreur est survenue.</b><br>Certaines fonctionnalités risquent des disfonctions.<br>Il est conseillé de redémarrer le logiciel.<br><em>Support: [email protected]<script cf-hash='f9e31' type="text/javascript">
/*  */</script></em></html>");
    private JButton copy = new JButton("Copier le rapport");
    private JButton close = new JButton("Ok");
    
    private Toolkit toolkit = Toolkit.getDefaultToolkit();
    private Clipboard cb = toolkit.getSystemClipboard();
    
    private DateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss");
    private Date date;

    private StringWriter sw = new StringWriter();
    private PrintWriter pw = new PrintWriter(sw);
    
    private Throwable e;
    
    public CustomDialog(final Throwable e) {
        
        date = new Date();
        this.e = e;
        
        this.setModal(true); //On rend notre boite de dialogue modale
        this.setTitle("Erreur");
        this.setResizable(false);
        this.setSize(new Dimension(400, 150));
        this.setLocationRelativeTo(null);
        
        JPanel messageContent = new JPanel() {

            /**
             *
             */
            private static final long serialVersionUID = 3692136522118161020L;

            protected void paintComponent(final Graphics g) {
                Icon icon = UIManager.getIcon("OptionPane.errorIcon");    
                BufferedImage image = new BufferedImage( icon.getIconWidth() , icon.getIconHeight() , BufferedImage.TRANSLUCENT );
                icon.paintIcon(null, image.getGraphics() , 0 , 0 );
                g.drawImage(image, 20 , 35, 48 , 48 , null);
                super.paintComponents(g);
            }
        };

        messageContent.add(Box.createRigidArea(new Dimension(400 , 0)));
        messageContent.add(Box.createRigidArea(new Dimension(70 , 0)));

        FlowLayout flow = new FlowLayout();
        flow.setAlignment(FlowLayout.RIGHT);
        flow.setVgap(5);
        flow.setHgap(5);
        JPanel buttons = new JPanel(flow);
        buttons.add(copy);
        buttons.add(close);
        final Container glass = (Container) this.getGlassPane();
        glass.setVisible(true);
        glass.setLayout(new BorderLayout());
        glass.add(buttons , BorderLayout.SOUTH);

        messageContent.add(message);

        close.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent event) {
                dispose();
            }            
        });

        copy.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent event) {
                cb.setContents( new StringSelection(getReport()) , null );             
            }            
        });

        this.setContentPane(messageContent);        
        
        this.setVisible(true);
    }
    
    private String getReport() {
        e.printStackTrace(pw);
        return new String( "Rapport d'erreur :\n"
                + "Version : " + "0.0.1" + "\n"
                + "Date : " + dateFormat.format(date) + "\n"
                + "Système d'exploitation : " + System.getProperty("os.name") + " " + System.getProperty("os.version") +"\n\n"
                + "StackTrace :\n" + sw.toString());
    }
    
}

 

TKuM2ih.png

 

 

Résumé :

 

  • Les boites de dialogue sont de petites fenêtres permettant d'afficher une information ou d'en demander une à l'utilisateur.
  • Elles figent le reste du programme tant qu'elles sont ouvertes.
  • Les boites de dialogues modales empêchent toute interaction avec le reste du logiciel tant qu'elle sont ouvertes.
  • Pour les boites de dialogue préfabriquées, on utilisera JOptionPane.
  • Pour les boites de dialogue personnalisées, on créera une classe qui hérite de JDialog.

 

 

JeremGamer

 

2cp1ED5.png


4 personnes aiment ça


2 Commentaires


Joli travail ! ;)

2 personnes aiment ça

Partager ce commentaire


Lien vers le commentaire
Partager sur d’autres sites

Créer un compte ou se connecter pour commenter

Vous devez être membre afin de pouvoir déposer un commentaire

Créer un compte

Créez un compte sur notre communauté. C’est facile !


Créer un nouveau compte

Se connecter

Vous avez déjà un compte ? Connectez-vous ici.


Connectez-vous maintenant