IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

AWT/Swing Java Discussion :

MVC en swing : Qu'est-ce qui va dans la vue et le controleur


Sujet :

AWT/Swing Java

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Rédacteur

    Avatar de millie
    Profil pro
    Inscrit en
    Juin 2006
    Messages
    7 015
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 7 015
    Par défaut MVC en swing : Qu'est-ce qui va dans la vue et le controleur
    Bonjour,

    J'ai rarement eu l'occasion de faire des applications graphiques type swing, et je regarderai quelques tutoriels à droite à gauche sur le respect de MVC avec swing.
    Et je suis tombé sur plusieurs cas qui fait que je ne sais pas exactement ce qui doit aller dans la vue et ce qui doit aller dans le controleur.

    D'ailleurs, ça m'embête un peu, car je me dis que cette architecture est tellement nase que quelque chose doit m'échapper .


    Imaginons que sur ma vue, j'ai un simple bouton, qui peut par exemple amener à l'ouverture de fichier (Fenêtre de dialogue où l'utilisateur choisi son fichier).

    Cas 1 :

    D'un côté, je vois des tutos qui mettent l'ActionListener du bouton directement sur la vue, puis passe par le contrôleur pour déclencher le traitement (ou l'action).
    => ce qui me dérange avec cette aspect, c'est finalement que la vue ne joue pas uniquement un rôle de vue, mais aussi de composant qui écoute. Et la demande de traitement au contrôleur est finalement mise dans la vue.
    Mais je ne crois pas que l'on puisse faire autrement pour certains type de traitement, comme les drag&drop de fichiers.

    D'un autre côté, je vois des tutos où c'est le contrôleur qui ajoute l'ActionListener sur le bouton de la vue
    => et là, ce qui me dérange, c'est que le contrôleur est au courant de l'implémentation de la vue (il sait déjà a priori que c'est du swing).

    Cas 2 :
    Ensuite, quand l'utiilisateur clique sur le bouton, cela ouvre une fenêtre attachée à l'autre vue. Mais qui s'occupe de l'attachement de la fenêtre ?
    - si c'est la vue, il faut y aller à coup d'instanceof, ce qui fait que ça ne respecte pas vraiment le principe de Liskov (même s'il y a un simple "attachView" sur l'interface de la vue)
    - si c'est le controleur, on retombe sur le cas où le controleûr est au courant que c'est du swing derrière



    Du coup, quelle stratégie adopter pour ces 2 cas ?


    Merci

  2. #2
    Membre très actif
    Avatar de william44290
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Juin 2009
    Messages
    400
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France

    Informations professionnelles :
    Activité : Responsable de service informatique

    Informations forums :
    Inscription : Juin 2009
    Messages : 400
    Par défaut
    Pour les simples fênetres je code tout dans le panel qui devient un VC. (le cas numéro 1)

    Pour les fênetres complexe je décompose. En particulier je dissocie en deux parties les Vues. Soit un panel d'affichage et un panel de bouton, une class métier typée controleur s'occupant d'instancier ces 2 vues et écoutants les boutons via une interface. Le Modèle n'étant qu'un mapping de table.

    Je ne comprends pas ton cas numéro 2.

    Sur le fond, le principe de découplage reste virtuel car d'une façon ou d'une autre le controleur dispose régulierement d'une référence sur la/les vues et sur le modéle.

  3. #3
    Rédacteur

    Avatar de millie
    Profil pro
    Inscrit en
    Juin 2006
    Messages
    7 015
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 7 015
    Par défaut
    Citation Envoyé par william44290 Voir le message
    Sur le fond, le principe de découplage reste virtuel car d'une façon ou d'une autre le controleur dispose régulierement d'une référence sur la/les vues et sur le modéle.
    Le problème n'est pas d'avoir une référence, mais c'était de ne pas avoir à connaître l'implémentation.


    Soit un panel d'affichage et un panel de bouton, une class métier typée controleur s'occupant d'instancier ces 2 vues et écoutants les boutons via une interface
    Donc, dans ton cas, c'est le controleur qui ajoute les listeners sur la vue ?





    Pour être plus précis, pour le cas 1, je ne savais pas s'il fallait faire (je n'ai pas mis les listeners sur le modèle) :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
     
    public interface MaVue {
      ....
    }
     
    public class SwingVue implements MaVue {
       JButton button = new JButton("etc");
       ....
       button.addActionListener(new ActionListener() {
          void run() {
              getController().executeAction(new MonAction(mesparamètres));
          }
       });
    }
     
    public Controlleur implements IController {
       MaVue vue = ViewFactory.get(MaVue.class);
       public void executeAction(Action a) {
           a.execute(); //pour simplifier
       }
    }
    Ou s'il fallait faire :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
     
    public interface MaVue {
      ....
    }
     
    public class SwingVue implements MaVue {
       JButton button = new JButton("etc");
    }
     
    public Controller implements IController {
       MaVue vue = ViewFactory.get(MaVue.class);
       public Controller() {
         ((SwingMaVue) vue).getJButton().addActionListener(new ActionListener() {
          void run() {
             Action a = new MonAction(mesparamètres));
             a.execute();
          }
       });
    }

    Pour le cas 2, si par exemple la vue principale est un JDesktopPane où l'on peut attacher d'autre vue. Cela correspond aux 2 cas suivants :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
     
    public interface SubView {
       void display();
    }
     
    public SwingOpenFileView implements SubView extends JDialog {
     ....
    }
     
    public interface MainView {
      public void attachSubView(SubView view);
    }
     
    public SwingMainView implements MainView extends JDesktopPane {
       //cette méthode peut être appelée au travers du controlleur
      public void attachSubView(SubView view) {
         if(view instanceof Component) 
            add((Component) view);
      }
    }
     
    public ControllerImpl implements Controller {
       ....
      public void attachSubView(SubView view) {
          getView().attachSubView(view); 
      }
    }
     
    public void OpenFileAction implements Action {
       //j'ai retiré le constructeur
       public void execute() {
            SwingOpenFileView v = new SwingOpenFileView(getController());
            getController().attachSubView(v);
       }
    }
    Ou :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    public ControllerImpl implements Controller {
       ....
      public void attachSubView(SubView view) {
          if(getView() instanceof JDesktopPane && view instanceof Component) {
              ((JDesktopPane) getView()).add((Component) view);
          }
      }
    }
    A priori, je voterai pour les premiers exemples qui présentent moins de contraintes, mais je voulais être sûr car j'ai déjà vu le contraire.

    Enfin, à noter que je n'aime pas vraiment l'architecture MVC, donc j'essaye de l'adapter comme je veux

  4. #4
    Membre très actif
    Avatar de william44290
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Juin 2009
    Messages
    400
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France

    Informations professionnelles :
    Activité : Responsable de service informatique

    Informations forums :
    Inscription : Juin 2009
    Messages : 400
    Par défaut
    Donc, dans ton cas, c'est le controleur qui ajoute les listeners sur la vue ?
    Oui, j'essaye de réaliser les vues les plus basiques possible.(Les demandes et critiques des utilisateur portent principalement sur ces dernières)

    pour le cas numéro 1 la version 1 est plus lisible mais la version 2 me semble plus conforme

    La vue qui appelle le controleur cela me semble anti-pattern.

    désolé pour le cas 2 cela me dépasse.

  5. #5
    Rédacteur

    Avatar de millie
    Profil pro
    Inscrit en
    Juin 2006
    Messages
    7 015
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 7 015
    Par défaut
    Citation Envoyé par william44290 Voir le message
    La vue qui appelle le controleur cela me semble anti-pattern.
    C'est par exemple ce que l'on voyait ici :
    http://baptiste-wicht.developpez.com...ion/mvc/#LII-C

  6. #6
    Membre très actif
    Avatar de william44290
    Homme Profil pro
    Responsable de service informatique
    Inscrit en
    Juin 2009
    Messages
    400
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France

    Informations professionnelles :
    Activité : Responsable de service informatique

    Informations forums :
    Inscription : Juin 2009
    Messages : 400
    Par défaut
    pour ma part lorsque que je travaille avec des composants les actions opérées sur le composant modifie une property du composant.

    Le controleur qui a instancié le composant Ecoute le changement d'état du composant et interagi en conséquence.

    Le composant n'a aucun lien avec le controleur.(plus exactement il ne sait pas si un ou plusieurs controleur l'écoute)

  7. #7
    Rédacteur/Modérateur

    Avatar de bouye
    Homme Profil pro
    Information Technologies Specialist (Scientific Computing)
    Inscrit en
    Août 2005
    Messages
    6 901
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 48
    Localisation : Nouvelle-Calédonie

    Informations professionnelles :
    Activité : Information Technologies Specialist (Scientific Computing)
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Août 2005
    Messages : 6 901
    Billets dans le blog
    54
    Par défaut
    Alors pour rappel (deja mentionne dans un autre topic il y a qq mois) :

    - la plupart des composants Swing fournis par defaut : la vue EST le controlleur, Swing utilisant plutot M V+C que MVC. Le composant dispose donc un unique modele (M) et une unique UI Delegate (V+C). Le modele influe sur l'etat de l'UI tandis que l'UI permet de modifier l'etat du modele.

    composant -> M -> V+C -> M

    Les codes sources des UI de base sont dispo dans les packages javax.swing.plaf.basic et javax.swing.plaf.metal (voir sources.zip a la racine du repertoire d'installation du JDK). Par exemple, il peut etre interressant et enrichissant d'aller lire le code source de BasicSliderUI si on desire implementer de nouveaux composants.

    Quand on change de LnF via l'UIManager par exemple, on change l'UI Delegate de chacun des composants affiches.

    - JavaFX utilise VC : il n'y a pas de modele dedie (pour le moment) et chaque controle JavaFX (le nom des composants en JavaFX) dispose d'une unique Skin (V) se charge de l'apparence et qui elle-meme delegue le comportement a un unique Behavior (C). On peut egalement faire V+C en faisant que la skin gere directement le comportement mais ce n'est pas trop recommande (certaines choses comme le fait qu'il n'y a pas de propagation des evenements claviers lorsque le controle est desactive sont gerees automatiquement par le Behavior).

    controle -> V -> C -> controle

    C'est comme cela que sont implementees les composants et les controles de base en Swing et JavaFX. Apres pour des interfaces plus complexes, a toi de voir si tu veux implementer une separation stricte des divers composantes M V et C.
    Merci de penser au tag quand une réponse a été apportée à votre question. Aucune réponse ne sera donnée à des messages privés portant sur des questions d'ordre technique. Les forums sont là pour que vous y postiez publiquement vos problèmes.

    suivez mon blog sur Développez.

    Programming today is a race between software engineers striving to build bigger and better idiot-proof programs, and the universe trying to produce bigger and better idiots. So far, the universe is winning. ~ Rich Cook

Discussions similaires

  1. Réponses: 8
    Dernier message: 29/02/2008, 14h27
  2. qu'est-ce qui cloche dans ma requete select??
    Par a-chan dans le forum Langage SQL
    Réponses: 3
    Dernier message: 07/07/2005, 11h35
  3. qu'est-ce qui cloche dans ma requete?
    Par a-chan dans le forum Langage SQL
    Réponses: 4
    Dernier message: 20/06/2005, 09h02
  4. Réponses: 1
    Dernier message: 21/02/2005, 12h40

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo