Reputation: 1807
I just started using Wicket, and while reading the book 'Wicket in action - by Martijn Dashorst and Eelco Hillenius' I try to implement some of the things I learn into small tests, but I seem to be making a mistake when I try to use an AjaxFallbackButton in a form. The code gets through the WicketTester tests but when I execute it I get an error that I don't fully understand.
What I'm trying to achieve is a page that shows a simple form where a user can input an expression and then clicks a button and the expression gets evaluated and displayed below the form. For now I'll stick to just displaying the contents of the form with a label. In the book there is an example just like this, but it doesn't use the AjaxFallBackButton which would allow for just the label to be updated instead of the entire page.
This is the html template:
<!DOCTYPE html>
<html xmlns:wicket="http://wicket.apache.org">
<head>
<meta charset="utf-8" />
<title>Wicket test</title>
<link href='http://fonts.googleapis.com/css?family=Yanone+Kaffeesatz:regular,bold' rel='stylesheet' type='text/css' />
<link rel="stylesheet" href="style.css" type="text/css" media="screen" title="Stylesheet" />
</head>
<body>
<div id="header">
<div id="logo">
<h1>Wicket test</h1>
</div>
</div>
<div id="body">
<h2>Simple test for wicket learning purposes</h2>
<p>
Test: <wicket:container wicket:id="message">text here</wicket:container>
</p>
<form wicket:id="form">
<input wicket:id="textField" type="text" />
<input wicket:id="evalButton" type="submit" value="evaluate" />
</form>
<p>
Result: <span wicket:id="evalResultLabel">result</wicket:container>
</p>
</div>
<div id="footer">
</div>
</body>
</html>
This is the corresponding java code:
public class HomePage extends WebPage {
private Label evalResultLabel;
private TextField<String> textField;
public HomePage() {
add(new Label("message", "lalala"));
Form<?> form = new Form("form");
textField = new TextField<String>("textField", new Model<String>("type expression here"));
form.add(textField);
form.add(new AjaxFallbackButton("evalButton", form) {
@Override
public void onSubmit(AjaxRequestTarget target, Form<?> form) {
String expr = textField.getModelObject();
evalResultLabel.setDefaultModelObject(expr);
if (target != null) {
target.add(evalResultLabel);
}
}
});
evalResultLabel = new Label("evalResultLabel", new Model<String>(""));
evalResultLabel.setOutputMarkupId(true);
add(form);
add(evalResultLabel);
}
}
The error message is as follows:
Unexpected RuntimeException - Last cause: Unable to find component with id 'form' in [Page class = HomePage, id = 0, render count = 1] Expected: '.form'. Found with similar names: ''
in the markup line:
<form wicket:id="form">
It does tell me when I run the WicketTester tests:
WARN - Component - Markup id set on a component that is usually not rendered into markup. Markup id: evalResultLabel3, component id: evalResultLabel, component tag: container.
Can anyone tell me what I'm doing wrong. I know I might learn more about this further in the book, but that kinda defeats the purpose of this test.
UPDATE: the same problem exists when I use a normal wicket Button:
public class HomePage extends WebPage {
private Label evalResultLabel;
private TextField<String> textField;
public HomePage() {
add(new Label("message", "lalala"));
Form form = new Form("form");
textField = new TextField<String>("textField", new Model<String>("type expression here"));
form.add(textField);
form.add(new Button("evalButton") {
@Override
public void onSubmit() {
String expr = textField.getModelObject();
evalResultLabel.setDefaultModelObject(expr);
}
});
evalResultLabel = new Label("evalResultLabel", new Model<String>(""));
add(form);
add(evalResultLabel);
}
}
Which is almost identical to the example given in the book. I can't see what I'm doing wrong. This book is fairly old though, using Wicket 1.2 or 1.3 I believe, maybe they changed something in the meantime? Any ideas how to fix this small piece of code?
Upvotes: 0
Views: 3273
Reputation: 1807
I'm sorry, I solved the problem. There was a problem with the embedded Jetty plugin I was using to test the code. When I built the application with Maven it suddenly started pulling in all this Jetty stuff, so I restarted the embedded server and behold: my code worked.
Upvotes: 0
Reputation: 5575
When you want to update some empty component via Ajax, setOutputMarkupId(true) doesn't do the trick. You'll need to user setOutputMarkupPlaceholder(true) as well and I'm currently unsure if this works on a wicket:container. You might have to change it to a span or something similar because Wicket needs some HTML component to expand when updating via Ajax...
A wicket:container with an empty label usually renders to nothing at all. So there is nothing that can be replaced by Ajax. This might seem cumbersome at first but it's an easy truth one gets used to pretty fast.
Upvotes: 3