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

Wicket Java Discussion :

Conditionner un affichage


Sujet :

Wicket Java

  1. #1
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut Conditionner un affichage
    Bonjour,

    J'ai un problème dans le dèv de mon appli, cela concerne l'affichage d'une Dataview. Je m'explique :
    Mon appli qui fait appel à un WS est chargée de récupérer le contenu d'un bloc de données qui contient une liste de Personne. J'affiche ensuite cette liste dans une Dataview.
    Cette liste peut :
    -contenir 1 ou n personnes -> aucun problème
    -contenir 0 personne -> liste vide j'affiche une Dataview vide, pas de problème
    -être NULL, dans ce cas je ne voudrais pas afficher la Dataview et c'est là que vient ma question car en Java il suffit de faire un test sur la liste et de ne pas créer la Dataview. Mais du côté HTML j'ai un wicket:id pour la Dataview qui ne trouve pas de correspondance côté JAVA.

    Pour remédier à cela, si ma liste est NULL je suis donc obligé de créer une Dataview avec le même wicket:id et de mettre son setVisible à FALSE.

    Cela marche mais c'est vraiment pas joli. N'y aurait-il pas un autre moyen de gérer cette condition, car cela est valable pour plein d'autres choses. Si je veux conditionner un affichage en JAVA je ne peux pas le faire en HTML.

  2. #2
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    8
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Octobre 2009
    Messages : 8
    Par défaut
    Non, je ne connais pas d'autre moyen car chaque composant HTML doit avoir sa correspondance en Java.

    Passer en setVisible(false) et la solution la plus propre.

  3. #3
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    On ne peut pas dire que cela soit très propre, cela revient à initialiser un composant qui nous servira à rien car on va le mettre visible(false).
    Mais bon si c'est la seule solution...

  4. #4
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    8
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Octobre 2009
    Messages : 8
    Par défaut
    Et bien il y a plusieurs façons de voir les choses, je pourrais aussi poser une autre question :

    - quelle est la signification d'un Null pour cette liste, et pourquoi faire une distinction avec le cas liste vide ?

    Pourquoi ne pas tout simplement créer une liste vide lorsque le WS renvoie null ? Comme ça pas besoin de setVisible(false)

  5. #5
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    Tout simplement parce qu'on me demande de retranscrire ce que retourne le WS.
    Une liste vide c'est une liste avec aucune occurrence mais c'est une liste quand même donc j'affiche la Dataview.
    En revanche une Liste qui vaut NULL ce n'est pas une liste, donc pas question d'afficher la DataView.

    Merci quand même de ton aide

  6. #6
    Membre émérite

    Inscrit en
    Décembre 2004
    Messages
    584
    Détails du profil
    Informations forums :
    Inscription : Décembre 2004
    Messages : 584
    Par défaut
    salut

    je voulais creuser le sujet un peu plus avant de répondre (j'ai comme une solution alternative en tete), mais pour l'immédiat voici ce que j'en dirai : ne pas toucher à setVisible, mais surcharger isVisible directement sur la listview.

    c'est en effet la bonne pratique recommandée : comme ça les composants maitrisent leur propre visibilité.

    voila, je regarderai de plus près le problème ce soir

    bonne journée
    joseph

  7. #7
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    Sur ces précieux conseil j'ai redéfini la méthode isVisible du composant Dataview et j'ai repassé un test avec un liste NULL.
    Et j'ai le message suivant : "argument [list] cannot be null"

    Voici mon code :
    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
     
    public class ResultatBlocPanel extends Panel{
    	public ResultatBlocPanel(String id, Resultat resultatWS) {
    		super(id);
     
    		final List <Personne> listeResultats = resultatWS.getListePersonne();
     
    		final DataView<Personne> dataView = new DataView<Personne>("liste", new ListDataProvider<Personne>(listeResultats)) {
    			public void populateItem(final Item<Personne> item) {
    				item.add(new Label("nom", item.getModelObject.getNom()));
    				item.add(new Label("prenom", item.getModelObject.getPrenom()));
    				item.add(new Label("cp", item.getModelObject.getCodePostal()));
    				item.add(new Label("ville", item.getModelObject.getVille()));
    				item.add(new Label("pays", item.getModelObject.getPays()));
    			}
    			public boolean isVisible(){
    				if(listeResultats != null){
    					return true;
    				}else{
    					return false;
    				}
    			}
    		};
    		add(dataView);
    	}
    }

  8. #8
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    8
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Octobre 2009
    Messages : 8
    Par défaut
    Oui joseph_p a raison : la méthode la plus élégante consisterait à surcharger isVisible(), puisqu'après tout c'est au composant de savoir s'il doit s'afficher ou non en fonction de son modèle.

    Sauf qu'effectivement le dataprovider n'est pas fait pour fonctionner avec une liste nulles :

    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
     
                /**
             * 
             * @param list
             *            the list used as dataprovider for the dataview
             */
    	public ListDataProvider(List<T> list)
    	{
    		if (list == null)
    		{
    			throw new IllegalArgumentException("argument [list] cannot be null");
    		}
     
    		this.list = list;
    	}
    Il faudrait que tu reféfinisse un DataProvider qui accepte une liste nulle, sauf qu'il me semble que pour éviter un plantage dès qu'il va tenter de calculer la taille de la liste il faudrait que ce DataProvider renvoie 0 pour getSize(). Ce qui revient exactement à avoir une liste vide.

    Ca me paraît bien compliqué et encore plus "sale" que setvisible(false).

  9. #9
    Membre émérite

    Inscrit en
    Décembre 2004
    Messages
    584
    Détails du profil
    Informations forums :
    Inscription : Décembre 2004
    Messages : 584
    Par défaut
    et pourquoi ne pas se contenter de faire en sorte que la liste fournie ne soit jamais nulle ?

    Quelque chose du genre :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
     
    final List <Personne> listeResultats;
    List<Personne> tempList = resultatWS.getListePersonne();
    if (tempList != null){
       listeResulats = tempList ;
    }else{
       listeResultats = new ArrayList<Personne>();
    }
    je pense que cela règlerait le problème.

    pour finir, j'ai croisé ça dans la Javadoc en question :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    /**
     * Allows the use of lists with dataview. The only requirement is that either list items must be
     * serializable or model(Object) needs to be overridden to provide the proper model implementation.
     * 
     * @author Igor Vaynberg ( ivaynberg )
     * @param <T>
     * 
     */
    public class ListDataProvider<T extends Serializable> implements IDataProvider<T>
    Espérons que Personne soit bien Serializable .

    ++
    joseph

  10. #10
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    Faire en sorte que la liste ne soit jamais NULL je veux bien mais la DataView s'affichera quand même ce que je voudrais éviter dans ce cas bien précis (mais j'ai bien peur que ce soit la seul solution).

    En revanche je comprend pas pourquoi la manière dont je redéfini isVisible() me provoque encore une erreur. Est-ce que je ne surcharge pas la méthode comme il le faut ?

    Et dernière précision, Personne est bien sérialisable.

  11. #11
    Membre émérite

    Inscrit en
    Décembre 2004
    Messages
    584
    Détails du profil
    Informations forums :
    Inscription : Décembre 2004
    Messages : 584
    Par défaut
    Je ne vois rien qui me saute aux yeux dans le isVisible proposé. Quelle est l'erreur apparaissant précisément ?

    Quelques recommandations toutefois :
    - en première approche, si j'utilise Java6, j'ajouterai perso l'annotation @Override :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
                            @Override
    			public boolean isVisible(){
                                (...)
    			}
    de la sorte, si la signature de la méthode diffère, il y aura une plus grande possibilité d'en être informé.

    - le code actuel utilise listeResultats. Cela n'a pas réellement besoin d'être, autant s'appuyer sur le modèle interne. En général cela peut se faire via un getModelObject(), mais le DataView semble spécifique (je n'utilise pas ce composant très souvent). En l'occurrence, il semble falloir passer par :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    public IDataProvider<T> getDataProvider()
    et de là, perso, j'irai m'appuyer sur la méthode int size(); de IDataProvider, qui me semble plus appropriée de façon générale.

  12. #12
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    Merci de votre aide. J'ai tourné le problème dans tout les sens. Mais quoi qu'il arrive, même si je fais en redéfinissant la méthode ou en mettant juste une setVisible(false) ou en testant le DataProvider. Il essaye toujours de construire ça Dataview quelque soit ça visibilité, donc il n'accepte pas la liste NULL.

    Je vais tourner le problème autrement mais je vous remercie beaucoup pour vos contributions.

  13. #13
    Membre émérite

    Inscrit en
    Décembre 2004
    Messages
    584
    Détails du profil
    Informations forums :
    Inscription : Décembre 2004
    Messages : 584
    Par défaut
    je ferai une démo complète ce soir et je la posterai si elle fonctionne

  14. #14
    Membre émérite

    Inscrit en
    Décembre 2004
    Messages
    584
    Détails du profil
    Informations forums :
    Inscription : Décembre 2004
    Messages : 584
    Par défaut
    bonjour

    je viens de réaliser un test, tout a bien fonctionné. Seule réelle correction apportée : passer de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    item.getModelObject.getVille()
    à
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    item.getModelObject().getVille()
    . Ceci dit, un bête IDE devrait avoir montré l'absence de parenthèses, donc je ne comprends pas très bien.

    Voici donc le code correspondant, sachant que ce n'est pas ce que je recommanderai mais juste pour illustrer la problématique présente.

    ResultatBlocPanel:
    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
    36
    37
    38
    39
    40
    41
     
    package org.demo.dataview;
     
    import java.util.ArrayList;
    import java.util.List;
     
    import org.apache.wicket.markup.html.basic.Label;
    import org.apache.wicket.markup.html.panel.Panel;
    import org.apache.wicket.markup.repeater.Item;
    import org.apache.wicket.markup.repeater.data.DataView;
    import org.apache.wicket.markup.repeater.data.ListDataProvider;
     
    public class ResultatBlocPanel extends Panel {
    	public ResultatBlocPanel(String id, Resultat resultatWS) {
    		super(id);
     
    		final List<Personne> listeResultats;
    		List<Personne> tempList = resultatWS.getListePersonne();
    		if (tempList != null) {
    			listeResultats = tempList;
    		} else {
    			listeResultats = new ArrayList<Personne>();
    		}
     
    		final DataView<Personne> dataView = new DataView<Personne>("liste",
    				new ListDataProvider<Personne>(listeResultats)) {
    			public void populateItem(final Item<Personne> item) {
    				item.add(new Label("nom", item.getModelObject().getNom()));
    				item.add(new Label("prenom",item.getModelObject().getPrenom()));
    				item.add(new Label("cp", item.getModelObject().getCodePostal()));
    				item.add(new Label("ville", item.getModelObject().getVille()));
    				item.add(new Label("pays", item.getModelObject().getPays()));
    			}
     
    			public boolean isVisible() {
    			      return (listeResultats != null) && !listeResultats.isEmpty();
    			}
    		};
    		add(dataView);
    	}
    }
    ResultatBlocPanel.html :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    <html xmlns:wicket="http://wicket.apache.org/dtds.data/wicket-xhtml1.4-strict.dtd">
        <head>
        </head>
        <body>
            <wicket:panel>
            	<table>
            		<tr wicket:id="liste"><td wicket:id="nom"></td><td wicket:id="prenom"></td><td wicket:id="cp"></td><td wicket:id="ville"></td><td wicket:id="pays"></td></tr>
            	</table>
            </wicket:panel>
        </body>
    </html>
    Personne :
    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
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    package org.demo.dataview;
     
    import java.io.Serializable;
     
    public class Personne implements Serializable {
    	private String nom;
    	private String prenom;
    	private String codePostal;
    	private String ville;
    	private String pays;
     
    	public String getNom() {
    		return nom;
    	}
     
    	public void setNom(String nom) {
    		this.nom = nom;
    	}
     
    	public String getPrenom() {
    		return prenom;
    	}
     
    	public void setPrenom(String prenom) {
    		this.prenom = prenom;
    	}
     
    	public String getVille() {
    		return ville;
    	}
     
    	public void setVille(String ville) {
    		this.ville = ville;
    	}
     
    	public String getPays() {
    		return pays;
    	}
     
    	public void setPays(String pays) {
    		this.pays = pays;
    	}
     
    	public void setCodePostal(String codePostal) {
    		this.codePostal = codePostal;
    	}
     
    	public String getCodePostal() {
    		return codePostal;
    	}
    }
    DataViewTestPage :
    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
    package org.demo.dataview;
     
    import java.util.ArrayList;
    import java.util.List;
     
    import org.apache.wicket.markup.html.WebPage;
     
    public class DataViewTestPage extends WebPage {
     
    	public DataViewTestPage(){
    		Resultat resultatWS = new Resultat();
    		add(new ResultatBlocPanel("dataviewEmpty", resultatWS ));
    		List<Personne> personnes = new ArrayList<Personne>();
    		Personne personne = new Personne();
    		personne.setNom("test");
    		personnes.add(personne);
    		resultatWS.setPersonnes(personnes ) ;
     
    		add(new ResultatBlocPanel("dataviewNonEmpty", resultatWS ));
    	}
    }
    DataViewTestPage.html :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    <html xmlns:wicket="http://wicket.apache.org/dtds.data/wicket-xhtml1.4-strict.dtd">
        <body>
            Empty data view
            <wicket:container wicket:id="dataviewEmpty">
            </wicket:container>
            <hr/>Non empty data view
            <wicket:container wicket:id="dataviewNonEmpty">
            </wicket:container>
        </body>
    </html>
    Parmi les améliorations que j'apporterai, il y a notamment :
    - ne jamais retourner null au lieu d'une liste, toujours retourner une liste nulle,
    - éviter de lier des composants directement à des valeurs, comme c'est le cas pour les labels utilisés dans l'exemple. En général cela revient plus tard hanter le développeur ayant codé la chose (vu que sans doute la valeur des champs sera éditée).
    Dans le cas présent, le code actuel:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    item.add(new Label("ville", item.getModelObject().getVille()));
    pourrait devenir par exemple :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    item.add(new Label("ville", new PropertyModel<String>(item.getModel(), "ville")));
    => relit à chaque accès au modèle la valeur associée, possibilité en plus de modifier la valeur contenue dans le PropertyModel (non utilisé ici).

    D'autres modèles sont utilisables, comme par exemple :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    item.add(new Label("ville", new AbstractReadOnlyModel<String>() {
     
    					@Override
    					public String getObject() {
    						return item.getModelObject().getVille();
    					}
    				}));
    => ce dernier se contente de lire à chaque fois la valeur qui va bien.

    Ne pas hésiter en cas de question.

    ++
    joseph

  15. #15
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    Si j'ai bien tout suivi, grâce à ton code de test, tu vas créer 2 ResultatBlocPanel. Le premier contient une liste de personnes NULL donc tu lui affecte une liste vide et grâce à isVisible() elle ne s'affiche pas.
    Pour l'autre ResultatBlocPanel l'affichage se fait normalement.

    Jusque la je pense avoir très bien compris ta démo, et je te remercie beaucoup des explications complémentaires. Cela répond clairement à mon interrogation, c'est à dire qu'il est impossible de faire quoi que se soit avec une DataView dont la liste en paramètre serait NULL (jouer sur l'affichage). Je suis donc obligé de passer par une liste vide.

    J'aurais quand même d'autres questions suite à cette belle démo :

    Voici donc le code correspondant, sachant que ce n'est pas ce que je recommanderai mais juste pour illustrer la problématique présente.
    Pourquoi ne le recommanderai tu pas ?

    Et dernière question, quand on utilise une Dataview, qu'elle soit visible(true) ou (false) c'est généralement pour représenter un structure tabulaire. Donc en HTML on construit un tableau. Pour ma part les entêtes de ce tableau sont en dur dans le code HTML:
    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
     
    <table>
    	<tbody>
    		<tr>
    			<th>Nom</th>
    			<th>Pr&eacute;nom</th>
    			<th>Ville</th>
    			<th>Code Postal</th>
    			<th>Pays</th>
    		</tr>
    		<tr wicket:id="dataviewPersonne">
    			<td wicket:id="nom">Nom</td>
    			<td wicket:id="prenom">Pr&eacute;nom</td>
    			<td wicket:id="ville">Ville</td>
    			<td wicket:id="cp">Code Postal</td>
    			<td wicket:id="pays">Pays</td>
    		</tr>
    	</tbody>
    </table>
    Ce qui fait que lorsque je rend ma Dataview invisible je garde quand même la structure du tableau avec les entêtes inscrite en dur dans le HTML. Ma question est : comment éviter cela c'est à dire rendre le <table> complètement invisible?

    Merci d'avance

  16. #16
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    8
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Octobre 2009
    Messages : 8
    Par défaut
    Citation Envoyé par Nico87 Voir le message
    Ma question est : comment éviter cela c'est à dire rendre le <table> complètement invisible?

    Merci d'avance
    Bonjour,

    dans ce cas je te conseille de regarder carrément du côté de la DataTable et DefaultDataTable :

    http://www.wicket-library.com/wicket...ter.SimplePage

    Ca te fera tout en un : tableau, headers du tableau, affichage avec setVisible(true|false). Il y a aussi des versions éditables et avec une pagination, en normal et en Ajax.

  17. #17
    Membre confirmé
    Inscrit en
    Février 2007
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 63
    Par défaut
    Merci bien!

  18. #18
    Membre émérite

    Inscrit en
    Décembre 2004
    Messages
    584
    Détails du profil
    Informations forums :
    Inscription : Décembre 2004
    Messages : 584
    Par défaut
    Autre solution communément adoptée : mettre un WebMarkupContainer autour des éléments à cacher/afficher, puis surcharger la seule méthode isVisible() du webmarkup container.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Conditionner l'affichage d'un composant MX ?
    Par ttone dans le forum Flex
    Réponses: 2
    Dernier message: 09/12/2008, 10h33
  2. Conditionner l'affichage dune entête d'un état
    Par pasbonte dans le forum IHM
    Réponses: 4
    Dernier message: 02/11/2008, 19h16
  3. Conditionner un affichage
    Par Arnaud Fournery dans le forum Langage SQL
    Réponses: 1
    Dernier message: 27/12/2007, 15h59
  4. Réponses: 3
    Dernier message: 16/03/2007, 14h26
  5. Réponses: 17
    Dernier message: 13/07/2006, 00h27

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