# Java > Interfaces Graphiques en Java > AWT/Swing >  MVC en swing : Qu'est-ce qui va dans la vue et le controleur

## millie

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'embte un peu, car je me dis que cette architecture est tellement nase que quelque chose doit m'chapper  ::aie:: .


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

*Cas 1 :* 

D'un ct, je vois des tutos qui mettent l'ActionListener du bouton directement sur la vue, puis passe par le contrleur pour dclencher le traitement (ou l'action).
=> ce qui me drange avec cette aspect, c'est finalement que la vue ne joue pas uniquement un rle de vue, mais aussi de composant qui coute. Et la demande de traitement au contrleur 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 ct, je vois des tutos o c'est le contrleur qui ajoute l'ActionListener sur le bouton de la vue
=> et l, ce qui me drange, c'est que le contrleur est au courant de l'implmentation de la vue (il sait dj a priori que c'est du swing). 

*Cas 2 :*
Ensuite, quand l'utiilisateur clique sur le bouton, cela ouvre une fentre attache  l'autre vue. Mais qui s'occupe de l'attachement de la fentre ?
- 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 (mme 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 controler est au courant que c'est du swing derrire



Du coup, quelle stratgie adopter pour ces 2 cas ?


Merci

----------


## william44290

Pour les simples fnetres je code tout dans le panel qui devient un VC. (le cas numro 1)

Pour les fnetres complexe je dcompose. En particulier je dissocie en deux parties les Vues. Soit un panel d'affichage et un panel de bouton, une class mtier type controleur s'occupant d'instancier ces 2 vues et coutants les boutons via une interface. Le Modle n'tant qu'un mapping de table.

Je ne comprends pas ton cas numro 2.

Sur le fond, le principe de dcouplage reste virtuel car d'une faon ou d'une autre le controleur dispose rgulierement d'une rfrence sur la/les vues et sur le modle.

----------


## millie

> Sur le fond, le principe de dcouplage reste virtuel car d'une faon ou d'une autre le controleur dispose rgulierement d'une rfrence sur la/les vues et sur le modle.


Le problme n'est pas d'avoir une rfrence, mais c'tait de ne pas avoir  connatre l'implmentation.





> Soit un panel d'affichage et un panel de bouton, une class mtier type 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 prcis, pour le cas 1, je ne savais pas s'il fallait faire (je n'ai pas mis les listeners sur le modle) :



```

```

Ou s'il fallait faire :


```

```


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 :


```

```

Ou : 


```

```

A priori, je voterai pour les premiers exemples qui prsentent moins de contraintes, mais je voulais tre sr car j'ai dj vu le contraire.

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

----------


## william44290

> Donc, dans ton cas, c'est le controleur qui ajoute les listeners sur la vue ?


Oui, j'essaye de raliser les vues les plus basiques possible.(Les demandes et critiques des utilisateur portent principalement sur ces dernires)

pour le cas numro 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.

dsol pour le cas 2 cela me dpasse.

----------


## millie

> 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

----------


## william44290

pour ma part lorsque que je travaille avec des composants les actions opres 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 consquence.

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

----------


## bouye

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.

----------


## sinok

Pour une explication un peu fine de l'application de ces patterns en Swing: 
http://www.jgoodies.com/articles/binding.pdf
http://www.jgoodies.com/articles/pat...nd-binding.pdf

Sachant qu'in fine l'auteur prche pour sa paroisse  savoir le pattern MVP au lieu du MVC. Le MVP dcorrlant totalement la vue du modle, la vue accdent au modle via le presenter (une sorte de contrleur sous strodes).

Bon l c'est vite fait car j'ai pas trop de temps devant moi, j'reviens ds que j'en ai un peu plus.

----------


## millie

Bon, en gros, il n'y a pas vraiment de rgle  ::mouarf::

----------


## uhrand

> Bon, en gros, il n'y a pas vraiment de rgle


Le but du contrleur est la traduction des actions de l'utilisateur en actions  excuter par le modle. L'attachement d'un ActionListener ou d'une fentre n'tant gnralement pas une action qui intresse le modle, il n'y a pas de raison pour placer a dans le contrleur (d'ailleur, je ne vois pas o "il faut y aller  coup d'instanceof" dans ce cas).

----------


## millie

> il n'y a pas de raison pour placer a dans le contrleur (d'ailleur, je ne vois pas o "il faut y aller  coup d'instanceof" dans ce cas).



En fait, je n'ai pas parl de instanceof pour ce cas l.
Le point qui m'embtait avec a, c'tait juste que la vue n'est pas seulement une vue, c'est une vue qui coute et qui transmet les demandes de traitements. Du coup, le nom me semble assez mal choisi.

----------


## bouye

Enfin bon quand on va lire les sources de l'API c'est un peu la foire  _instanceof_ chez Sun...

A noter que les UI des divers _AbstractButton_ (_JButton_, _JRadioButton_, etc...) disposent bien d'une sparation entre V et C contrairement  d'autre _JComponent_. Et ici c'est  nouveau la vue qui instancie le contrleur. Il faut dire aussi que le controleur d'un bouton est plutot simpliste  (juste vrification des touches du clavier et des clics sur toute la surface du composant) par rapport  ce que peut tre celui d'une vue plus complexe comme peut l'tre le controleur d'un _JSlider_ qui dpent fortement de la forme de son apparence.

----------


## uhrand

> la vue n'est pas seulement une vue, c'est une vue qui coute


C'est courant d'avoir une vue qui coute, car elle coute souvent le modle. Alternativement, nous pourrions faire implmenter l'ActionListener par le contrleur. Dans ce cas, c'est le contrleur qui coute directement. Mais a change rien au principe MVC.

----------


## Chatanga

Dans le monde des IHM, le MVC se dcline en pratique rcursivement de la manire suivante :

V' = M + V + C
Voire, dans le cas de Swing notamment :

V' = M + (V + C)
Avec ce dcoupage de Swing et en imaginant une application basique, on pourrait obtenir le rsultat suivant :

MonApplication(V) = MonModele(M) + MonFormulaire(V) + MonControlleurFormulaire(C)
MonFormulaire(V) = JComboBox(V) + ...(V) + ...(V)
JComboBox(V) = ComboBoxModel(M) + ComboBoxUI(V+C)
Remarque : personnellement, je cre souvent intgralement mes vues applicatives (ici MonFormulaire) sous NetBeans sans toucher au code (donc sans aucun binding).

Pour dtailler le cas d'une JComboBox, quand cette dernire installe son ComponentUI (qu'elle n'instancie d'ailleurs pas, mais dont elle demande simplement une instance approprie  l'UIManager), elle ignore ce qu'il fait concrtement (elle n'utilise d'ailleurs mme pas le fait que c'est un ComboBoxUI). Une JComboBox ignore ainsi que, pour la plupart des _Look And Feel_, l'instance de ComboBoxUI va lui ajouter un champ de texte, un bouton, un menu surgissant et cbler tout se joli monde. De fait, c'est bien le contrleur le chef d'orchestre, le JComponent englobant (la JComboBox ici) n'tant qu'une coquille vide pour le MVC (pour ce qui est de la dlgation du rendu, c'est autre chose). Nanmoins, comme tout ce petit monde est finalement cach dans la JComboBox, on peut quand mme dire que, dans Swing, vue et contrleur sont fusionns, mais sans pour autant remettre en cause l'approche MVC.

Sachant cela, on peut dire que la vue ne doit jamais connatre son modle, que seul le controleur doit pouvoir le faire, quitte  l'embarquer dans la vue pour donner la sensation suivante.



```
new JComponentX(new Model()); // Le composant Swing "observe" le modèle.
```

D'un certaine manire, tout se rsume  une question de perspective. L o le distinguo doit cependant s'oprer clairement, c'est lorsqu'il s'agit d'une vue et d'un modle mtier.

UNE VUE NE DOIT JAMAIS ACCEDER DIRECTEMENT A UN MODELE METIER, C'EST A UN CONTROLEUR DE LIER LES DEUX.
Par exemple, une vue gographique a le droit de manipuler apparemment directement un modle graphique interne dont les objets seraient des formes gorfrences, mais ne devrait en aucun cas jouer directement avec le modle de donnes mtier de l'application dont les objets seraient, par exemple, des voitures voluant sur des routes. Un contrleur s'impose pour connecter les deux.

----------


## uhrand

> UNE VUE NE DOIT JAMAIS ACCEDER DIRECTEMENT A UN MODELE METIER, C'EST A UN CONTROLEUR DE LIER LES DEUX.


Ca c'est une mise en uvre plus rcente de la conception MVC. Elle place le contrleur entre le modle et la vue. La principale diffrence entre cette conception et la version plus traditionnelle de MVC est que les notifications de modifications d'tat des objets de modle sont communiques  la vue par le contrleur. Par consquent, le contrleur sert d'intermdiaire pour le flux de donnes entre le modle et la vue dans les deux directions. Les objets d'affichage, comme toujours, utilisent le contrleur pour traduire les actions de l'utilisateur en mises  jour de proprits du modle. Mais en plus, les modifications d'tat du modle sont communiques  la vue par le biais d'objets de contrleur d'une application. Cet MVC modifi permet de dcoupler plus compltement le modle de la vue.

----------

