This Confluence has been LDAP enabled, if you are an ASF Committer, please use your LDAP Credentials to login. Any problems file an INFRA jira ticket please.

Child pages
  • How to repaint a ListView via Ajax
Skip to end of metadata
Go to start of metadata

You can't, you need to put it into a WebMarkupContainer and repaint that container instead.
More
If you take a closer look at the markup, and the markup that
gets generated, you can clearly see the problem for a listview:

In the server side markup:

<ul>
<li wicket:id="listitem"><span wicket:id="label">some value</span></li>
</ul>

In the client side markup:

<ul>
<li><span>foo</span></li>
<li><span>bar</span></li>
<li><span>foobar</span></li>
</ul>

What you typically want to do is to redraw the complete <ul></ul>
part, because most browsers really don't appreciate when you replace
parts of a tag, especially when you are working with a <table>.

As you can see in this example, the <ul> tag is not a component, and
Wicket is not aware of it. Even if you were to do:
listview.setOutputMarkupId(true), this wouldn't work, as the listview
itself doesn't have a tag associated with it.

That is why you need to provide the WebMarkupContainer yourself as a
wrapper for the listview.

[Thanks to Igor & Martijn for the original postings to the Wicket-User list. Gwyn 22:32, 21 Aug 2006 (BST)]

To repaint a WebMarkupContainer on an ajax submit (or edit or whatever), add the container to the AjaxRequestTarget:

AjaxButton button = new AjaxButton("button1") {     
    protected void onSubmit(AjaxRequestTarget target, Form form) {
        target.addComponent(<your WebMarkupContainer variable>);     
    }

Example

Here's one working example. It displays a table with 5 rows, with some random strings, and updating with the current date. It is designed to be an actually complete example, for those of us that understand the idea of what is said above, but not necessarily how to go about doing that. (And actually presenting both the markup and the backing code)

Markup Page

<?xml version="1.0" encoding="UTF-8"?>
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:wicket="http://wicket.apache.org/">
  <body>
      <table wicket:id="theContainer">
        <tr><th>index</th><th>name</th><th>date</th></tr>
        <tr wicket:id="hateList">
            <td><span wicket:id="hateIndex">index</span></td>
            <td><span wicket:id="hateName">name</span></td>
            <td><span wicket:id="hateDate">date</span></td>
        </tr>
      </table>
  </body>
</html>

Backing Page

public class AjaxListPage
    extends Page
{

    public AjaxListPage()
    {

        //get the list of items to display from provider (database, etc)
        //in the form of a LoadableDetachableModel
        IModel hateList =  new LoadableDetachableModel()
        {
            protected Object load() {
                return getHateList();
            }
        };

        ListView hateView = new ListView("hateList", hateList)
        {
            protected void populateItem(final ListItem item) {
                MyListItem mli = (MyListItem)item.getModelObject();
                item.add(new Label("hateName", mli.name));
                item.add(new Label("hateDate", mli.date.toString()));
                item.add(new Label("hateIndex", mli.index.toString()));
            }
        };

        //encapsulate the ListView in a WebMarkupContainer in order for it to update
        WebMarkupContainer listContainer = new WebMarkupContainer("theContainer");
        //generate a markup-id so the contents can be updated through an AJAX call
        listContainer.setOutputMarkupId(true);
        listContainer.add(new AjaxSelfUpdatingTimerBehavior(Duration.seconds(5)));
        // add the list view to the container
        listContainer.add(hateView);
        // finally add the container to the page
        add(listContainer);
    }

    // just keep randomizing the values, for display, so you can see it's updating.
    private List getHateList() {
        List ret = new ArrayList();
        for (int i = 0; i < 5; i++) {
            MyListItem x =  new MyListItem();
            x.name = RandomStringUtils.randomAlphabetic(10);
            x.date = new Date();
            x.index = x.date.getSeconds();
            ret.add(x);
        }
        return ret;

    }

    // a very simple model object just to have something concrete for an example
    private class MyListItem {
        public String name;
        public Date date;
        public Integer index;
    }
}
  • No labels