-
1. Re: Binding ValueListBox with <select/> html tag
jfuerth Apr 22, 2013 11:01 AM (in response to jmbarone)Hi Jose,
I should be able to help you get to the bottom of this if you can provide an example class that demonstrates the problem. Would you please respond with a complete @Templated class (and its corresponding .html file) that exhibits this problem?
Thanks,
Jonathan
-
2. Re: Binding ValueListBox with <select/> html tag
jmbarone Apr 23, 2013 8:33 AM (in response to jfuerth)Ok Jonathan ... i will try to explain the problem, but let me say that it's a simple and plain example.
Here goes the html view:
<!DOCTYPE html>
<html>
<form>
<label for="tipo">Tipo</label>
<select data-field="tipoMateriaPrima" id="tipo"></select><br>
<label for="nombre">Nombre</label>
<input id="nombre" type="text" data-field="nombre"><br>
<label for="cantidad">Cantidad</label>
<input data-field="cantidad" id="cantidad" type="number">
<select data-field="unidadMedida" id="unidadMedida"></select><br>
<label for="lote">Lote</label>
<input data-field="nroLote" id="nroLote" type="number"><br>
<label for="proveedor">Proveedor</label>
<select data-field="proveedor" id="proveedor"></select>
<label for="loteProveedor">Lote del proveedor</label>
<input data-field="loteProveedor" id="loteProveedor"><br>
<label for="factura">Factura</label>
<input data-field="factura" id="factura"><br>
<label for="tercerizacion">Tercerizacion</label>
<select data-field="tercerizacion" id="tercerizacion"></select><br>
<button data-field="submit">Ok</button>
</form>
</html>
It´s a pretty simple html, with two select´s, on fields "tercerizacion" and "proveedor" (we're talking a little spanish here )
Ok, then the "controller" class:
@Templated("MateriaPrimaView.html")
public class MateriaPrimaController extends Composite {
Logger logger = Logger.getLogger("MateriaPrimaView");
@Inject
Event<MateriaPrima> event;
@Inject
@AutoBound
private DataBinder<MateriaPrima> dataBinder;
@Inject
@DataField
@Bound
private ListBox tipoMateriaPrima;
@Inject
@DataField
@Bound
private TextBox nombre;
@Inject
@DataField
@Bound
private TextBox cantidad;
@Inject
@DataField
@Bound
private ListBox unidadMedida;
@Inject
@DataField
private TextBox nroLote;
@Inject
@DataField
@Bound
private ListBox proveedor;
@Inject
@DataField
@Bound
private TextBox loteProveedor;
@Inject
@DataField
@Bound
private TextBox factura;
@Inject
@DataField
@Bound
private ListBox tercerizacion;
@Inject
@DataField
private Button submit;
public MateriaPrimaController(){
}
}
@PostConstruct
public void init(){
tipoMateriaPrima.addItem("ITEM_1");
tipoMateriaPrima.addItem("ITEM_2");
}
public void setModelInstance(MateriaPrima mp){
dataBinder.setModel(mp, InitialState.FROM_MODEL);
dataBinder.getModel();
}
@EventHandler("submit")
private void submit(ClickEvent e){
logger.info("submit");
event.fire(dataBinder.getModel());
}
}
And finally the "App" class:
@EntryPoint
public class App {
@Inject
private MateriaPrimaController mpc;
@PostConstruct
public void init(){
MateriaPrima mp = new MateriaPrima("Materia 1", 5,
UNIDAD_MEDIDA.Kg, new TipoMateriaPrima("ITEM_2"),
new Tercerizacion("Tercerizacion 1"));
mp.setLoteProveedor("345RT");
mp.setNroLote(6734);
mp.setFactura("A3490");
mp.setProveedor(new Proveedor("Proveedor1"));
mpv.setModelInstance(mp);
RootPanel.get().add(mpc);
}
}
It´s really simply, i want to bound a ComboBox with a list of values, it´s an "all time" feature for programmers.
I think ... is this the right way with Errai?
Also, continue the good work with the framework, it's awesome.
Thanks.
-
3. Re: Binding ValueListBox with <select/> html tag
jfuerth Apr 26, 2013 1:06 PM (in response to jmbarone)Hi Jose,
Thanks for taking the time to communicate these details! The real problem is that ListBox doesn't implement HasValue, so Errai's Data Binding feature doesn't know how to set/get the selected item from the combo box, and it also doesn't know how to observe it for changes to the selection.
I've worked with your code and found a clean solution to the problem: you can subclass ListBox and implement HasValue<String> like this:
import com.google.gwt.event.dom.client.ChangeEvent; import com.google.gwt.event.dom.client.ChangeHandler; import com.google.gwt.event.logical.shared.ValueChangeEvent; import com.google.gwt.event.logical.shared.ValueChangeHandler; import com.google.gwt.event.shared.HandlerRegistration; import com.google.gwt.user.client.ui.HasValue; import com.google.gwt.user.client.ui.ListBox; public class BindableListBox extends ListBox implements HasValue<String> { public BindableListBox() { addChangeHandler(new ChangeHandler() { @Override public void onChange(ChangeEvent event) { ValueChangeEvent.fire(BindableListBox.this, getValue()); } }); } @Override public HandlerRegistration addValueChangeHandler(ValueChangeHandler<String> handler) { return addHandler(handler, ValueChangeEvent.getType()); } @Override public String getValue() { return getItemText(getSelectedIndex()); } @Override public void setValue(String value) { setValue(value, true); } @Override public void setValue(String value, boolean fireEvents) { int foundIndex = -1; for (int i = 0; i < getItemCount(); i++) { if (value.equals(getItemText(i))) { foundIndex = i; break; } } if (foundIndex == -1) { // didn't find a match. we can add the value. addItem(value); setSelectedIndex(getItemCount() - 1); } if (fireEvents) { ValueChangeEvent.fire(this, value); } } }
Once you have this BindableListBox, just change the ListBox injection points in MateriaPrimaController to BindableListBox, like this:
@Inject @DataField @Bound private BindableListBox proveedor;
Hope that helps!
-Jonathan
-
4. Re: Binding ValueListBox with <select/> html tag
jmbarone Apr 27, 2013 11:40 AM (in response to jfuerth)Jonathan: thanks for the response.
With ListBox it works directly ... but i want to work with the values, not with a string representation of them.
I mean, it will be more simply and natural to add the values to a gwt component and then ask for the selected value obtained from the user, without the boilerplate of what string is what value in my model.
More precisely ... i want to add the Proveedor values to a list and then obtain which Proveedor was selected for the user ... simple.
It's different to add the names to the list and then obtain the selected name and "calculate" wich Proveedor corresponds with that name ... appears more procedural against an object model.
What do you think?
Thanks
-
5. Re: Binding ValueListBox with <select/> html tag
jmbarone Apr 30, 2013 8:35 AM (in response to jmbarone)Well ... i have it working now
How? ... simple, change it to 2.3.0.CR1 version of Errai.
Now i can use the ValueListBox binded to <select /> html tags and using objects of my domain, not strings.
Other thing that matters is to create the equals and hash on the domain classes, without that the combo boxes always appends new values.
Thanks and i hope this can help someone out there.
-
6. Re: Binding ValueListBox with <select/> html tag
jfuerth Apr 30, 2013 9:28 AM (in response to jmbarone)Oh, your solution is even better. I didn't know about ValueListBox!
Thanks for the tip!
-Jonathan