60 votes

Didacticiel de plusieurs pages dans Google Web Toolkit (GWT)

J'ai juste commencé à apprendre le Google Web Toolkit (GWT). Comment puis-je faire différentes pages HTML dans mon application GWT?

Par exemple, je veux créer une application pour un magasin de livre. Dans cette application, je vais avoir trois pages:

  1. Les pages d'accueil où je serai heureux de l'utilisateur et offrent à l'utilisateur des livres
  2. Page pour rechercher des livres par catégories et de visualiser les détails (utilisation des widgets GWT)
  3. Consultez la documentation en ligne.

Bien sûr, il pourrait y avoir d'autres pages comme les données de l'utilisateur, ajouter un nouveau livre, etc. Alors, quelle est la meilleure façon de faire différentes pages en GWT et comment puis-je faire de la navigation de page en page? Existe-il des exemples ou des tutoriels? Ou dois-je encore besoin de créer différentes pages quand je peux créer un ensemble de l'application en une seule page?

74voto

Chris Ruffalo Points 1683

Ce que je fais habituellement dans ce genre de situations est la conception de la page web cadre de la première. Je vais avoir un div pour l'en-tête, le menu latéral et le pied de page. Je vais aussi avoir un div dans mon code HTML pour le contenu principal.

Exemple:

<html xmlns="http://www.w3.org/1999/xhtml">
    <head>
        <meta name='gwt:module' content='org.project.package.Core=org.project.package.Core'>
    </head>
    <body>
        <!-- Load the JavaScript code for GWT -->
        <script language="javascript" src="ui/org.project.package.ui.Core.nocache.js"></script>

        <!-- For some unknown reason in Internet Explorer you have to have cellpadding/spacing ON THE ELEMENT and not on the STYLE if it is in the body tag like this -->
        <table id="wrapper" cellpadding="0" cellspacing="0" style="width: 100%;height: 100%;">

             <!-- Header row -->
             <tr style="height: 25%;">
                 <td colspan="2" id="header"></td>
             </tr>

             <!-- Body row and left nav row -->
             <tr style="height: 65%;">
                 <td id="leftnav"></td>
                 <td id="content"></td>
             </tr>

             <!-- Footer row -->
             <tr style="height: 10%;">
                <td colspan="2" id="footer"></td>
             </tr>

        </table>

        <!-- This iframe handles history -->
        <iframe id="__gwt_historyFrame" style="width:0;height:0;border:0"></iframe>
    </body>
</html>

(Si vous le souhaitez <div> base de mises en page, n'hésitez pas à les utiliser à la place.)

Alors que vous construisez votre point d'entrée (dans mon cas Core.java) comme vous le feriez normalement, le réglage de chacun des éléments en tant que de besoin.

RootPanel.get("header").add(new Header());
RootPanel.get("leftnav").add(new NavigationMenu());
RootPanel.get("footer").add(new Footer());

Il est, bien sûr, possible d'avoir une statique du pied de page et en-tête, mais c'est ni ici ni là.

J'ai aussi une classe abstraite appelée "Contenu". Les objets de contenu étendre "Composite" et ont différentes méthodes pour simplifier la création et la présentation d'une nouvelle page. Chaque page que j'ai créer pour cette application, que ce soit un écran d'aide, à l'écran de recherche, panier d'achat, ou quoi que ce soit d'autre, est de type Content.

Maintenant, ce que j'ai à faire est de créer une classe appelée "ContentContainer". C'est un singleton qui est responsable de la gestion du "contenu" de l'élément. Il a une méthode "setContent" qui accepte les objets de type "Contenu". Ensuite, il élimine en principe rien dans le "contenu" <td> et le remplace avec ce widget (Composite) est attribué par le "setContent" la méthode. Le setContent méthode traite aussi de l'histoire et de la barre de titre de la gestion. Fondamentalement, la ContentContainer sert à regrouper tous les différents points de liaison que vous avez à faire si chaque contenu de la page a à "savoir" à propos de toutes les fonctions qu'il doit effectuer.

Enfin, vous avez besoin d'un moyen pour arriver à cette page, à droite? C'est simple:

ContentContainer.getInstance().setContent(new Search());

Mettre le ci-dessus dans le cadre d'un événement de clic quelque part et que vous êtes d'or.

Les seules choses que vos autres widgets besoin d'être lié à la ContentContainer et le type de Contenu qu'ils ajoutent.

Les inconvénients que je peux voir à ChrisBo de l'approche, vous avez une liste qui doit être maintenu de jetons -> pages. L'autre inconvénient que je peux voir, c'est que je ne vois pas comment vous pouvez avoir une histoire réelle du système avec cette méthode.

Une chose qu'il ne proposons plus de mon approche, c'est que tous les choix sont assez centralisée. Je voudrais utiliser une sorte de Enum ou au moins une classe statique avec les valeurs de Chaîne m'empêcher de mongling des liens.

Dans les deux cas, je pense que le point peut être résumé comme ceci: permuter le contenu de certains élément de la page en fonction de ce que votre utilisateur clique sur les actions de votre utilisateur(s) effectuer.

20voto

Chris Boesing Points 2477

Je voudrais utiliser le lien Hypertexte et de l'Histoire de la classe. La bonne chose à propos de l'Hyperlien de la classe, c'est qu'elle définit ce jeton(par exemple,#foobar), et tout ce que vous avez à faire, c'est la capture de l'événement est déclenché lorsque la valeur du jeton est changé(ValueChangeEvent). Dans le gestionnaire d'événements vous suffira alors de remplacer les pages.

Exemple: l'adresse de la Page de bienvenue: www.yourpage.com/#home sur cette page un lien vers la "parcourir le livre"-page, lorsque le lien est cliqué, la nouvelle adresse serait quelque chose comme ceci: www.yourpage.com/#browse

Et voici le code:


public class MainEntryPoint implements EntryPoint, ValueChangeHandler {
    VerticalPanel panel = new VerticalPanel();
    Label label=new Label();
    public void onModuleLoad() {
        Hyperlink link1 = new Hyperlink("books", "browse");
        Hyperlink link2 = new Hyperlink("user details", "details");
        panel.add(link1);
        panel.add(link2);
        panel.add(label);
        RootPanel.get().add(panel);
        History.addValueChangeHandler(this);
        //when there is no token, the "home" token is set else changePage() is called.
        //this is useful if a user has bookmarked a site other than the homepage.
        if(History.getToken().isEmpty()){
            History.newItem("home");
        } else {
            changePage(History.getToken());
        }
    }

9voto

Chloe S. Points 71

Génial! J'ai combiné Chris R. la réponse de Chris Boesing est à venir avec ce:

C'est le "index" page de démarrage

public class Index implements EntryPoint, ValueChangeHandler<String> {
    public void onModuleLoad() {
        History.addValueChangeHandler(this);
        if (History.getToken().isEmpty()) History.newItem("index");
        Composite c = new Login(); 
        FlowControl.go(c);
    }

    public void onValueChange(ValueChangeEvent<String> e) {
        FlowControl.go(History.getToken());
    }
}

C'est le contrôleur, ou ContentContainer selon Chris R.

public class FlowControl {
private static FlowControl instance;
private FlowControl() {}
public static void go(Composite c) {
    if (instance == null) instance = new FlowControl(); // not sure why we need this yet since everything is static.
    RootPanel.get("application").clear();
    RootPanel.get("application").getElement().getStyle().setPosition(Position.RELATIVE); // not sure why, but GWT throws an exception without this. Adding to CSS doesn't work.
    // add, determine height/width, center, then move. height/width are unknown until added to document. Catch-22!
    RootPanel.get("application").add(c);
    int left = Window.getClientWidth() / 2 - c.getOffsetWidth() / 2; // find center
    int top = Window.getClientHeight() / 2 - c.getOffsetHeight() / 2;
    RootPanel.get("application").setWidgetPosition(c, left, top);
    History.newItem(c.getTitle()); // TODO: need to change and implement (or override) this method on each screen
}

public static void go(String token) {
    if (token == null) go(new Login());
    if (token.equals("cart")) go(new Cart());
    if (token.equals("login")) go(new Login());
    // Can probably make these constants in this class
}

Ensuite, vous pouvez poivre liens hypertexte et les Boutons n'importe où dans votre code. (N'ai pas essayé les liens hypertexte).

    Button submit = new Button("Submit");
    submit.addClickHandler(new ClickHandler() {
        public void onClick(ClickEvent event) {
            FlowControl.go(new MyScreen());             
        }           
    });

J'ai ajouté un div de mon code HTML

<!-- This is where the application will reside within. It is controlled by FlowControl class. -->
<div id="application"></div>

Et maintenant, tous les écrans doivent appeler initWidget() dans le constructeur au lieu d'ajouter à RootPanel, car il est un Composite de classe maintenant, comme

    initWidget(myPanel); // all composites must call this in constructor

5voto

mives Points 829

Si vous voulez que ce soit FULL AJAXified (comme une application de bureau), vous n'avez besoin que d'une seule page. Ensuite, changez simplement le contenu du corps en fonction du lien.

En outre, il existe un groupe Google pour GWT qui est très actif, et je sais que cela a déjà été demandé, il vous suffit d’utiliser la fonctionnalité "recherche".

1voto

Helpa Points 462

GWT Multipage - Cadre simple pour applications multi-page-GWT.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X