我已经熟悉GWTP。我试图输出一个表,其中包含JSON值,这是在Piriti映射器的帮助下进行的。这不是一个真正的项目代码,只是一种理解GWTP的尝试,因此这可能不是最漂亮的解决方案(实际上,这并不是肯定的解决方案)。这是此过程中涉及的两个演示者:FirstPresenter
(使用ProductListPresenter
,它是一个小部件,我不确定此处是否应使用该小部件,但根据this conversation的说法,小部件可以解决问题):
public class FirstPresenter extends
Presenter<FirstPresenter.MyView, FirstPresenter.MyProxy> {
public static final Object SLOT_RATE = new Object();
public static final Object SLOT_PRODUCT = new Object();
private IndirectProvider<ProductListPresenter> productListFactory;
public interface MyView extends View {
public Panel getListProductPanel();
}
@Inject ProductListPresenter productListPresenter;
@ProxyCodeSplit
@NameToken(NameTokens.first)
public interface MyProxy extends ProxyPlace<FirstPresenter> {
}
@Inject
public FirstPresenter(final EventBus eventBus, final MyView view,
final MyProxy proxy, Provider<ProductListPresenter> productListFactory) {
super(eventBus, view, proxy);
this.productListFactory = new StandardProvider<ProductListPresenter>(productListFactory);
}
@Override
protected void revealInParent() {
}
@Override
protected void onBind() {
super.onBind();
}
@Inject
PlaceManager placeManager;
@Override
protected void onReset() {
super.onReset();
setInSlot(SLOT_PRODUCT, null);
for (int i = 0; i < 2; i++) { //TODO: change hardcoded value
productListFactory.get(new AsyncCallback<ProductListPresenter>() {
@Override
public void onSuccess(ProductListPresenter result) {
addToSlot(SLOT_PRODUCT, result);
}
@Override
public void onFailure(Throwable caught) {
}
});
}
}
}
ProductListPresenter
:public class ProductListPresenter extends
PresenterWidget<ProductListPresenter.MyView> {
@Inject ProductListPiritiJsonReader reader;
public interface MyView extends View {
public Label getNameLabel();
public Label getCompanyLabel();
public Label getSerialLabel();
public Label getPricesLabel();
}
@Inject
public ProductListPresenter(final EventBus eventBus, final MyView view) {
super(eventBus, view);
}
@Override
protected void onBind() {
super.onBind();
}
@Override
protected void onReset() {
super.onReset();
try {
RequestBuilder rb = new RequestBuilder(RequestBuilder.GET, "/jsongwtproject/products.json");
rb.setCallback(new RequestCallback() {
@Override
public void onResponseReceived(Request request, Response response) {
ProductList productList = reader.read(response.getText());
for (Product product : productList.getProductList()) {
fetchDataFromServer();
}
}
@Override
public void onError(Request request, Throwable exception) {
Window.alert("Error occurred" + exception.getMessage());
}
});
rb.send();
}
catch (RequestException e) {
Window.alert("Error occurred" + e.getMessage());
}
}
//Takes the JSON string and uses showProductListData(String jsonString) method
public void fetchDataFromServer() {
try {
RequestBuilder rb = new RequestBuilder(RequestBuilder.GET, "/jsongwtpproject/products.json");
rb.setCallback(new RequestCallback() {
@Override
public void onResponseReceived(Request request, Response response) {
showProductListData(response.getText());
}
@Override
public void onError(Request request, Throwable exception) {
Window.alert("Error occurred" + exception.getMessage());
}
});
rb.send();
}
catch (RequestException e) {
Window.alert("Error occurred" + e.getMessage());
}
}
//Uses Piriti mappers to take JSON values
private void showProductListData(String jsonString) {
ProductList productList = reader.read(jsonString);
for (Product product : productList.getProductList()) {
StringBuffer priceSb = new StringBuffer();
for (Double price : product.getPrices()) {
priceSb.append(price + ", ");
}
getView().getNameLabel().setText(product.getName());
getView().getCompanyLabel().setText(product.getCompany());
getView().getSerialLabel().setText(product.getSerialNumber());
getView().getPricesLabel().setText(priceSb.toString());
//break;
}
}
}
和
ProductListView.ui.xml
:<g:HTMLPanel>
<table border="1">
<tr>
<td><g:Label ui:field="nameLabel" /> </td>
<td><g:Label ui:field="companyLabel" /> </td>
<td><g:Label ui:field="serialLabel" /> </td>
<td><g:Label ui:field="pricesLabel" /> </td>
</tr>
</table>
</g:HTMLPanel>
当前,JSON中有两种产品。
这是此代码的结果:出现带有
Product1
的第一行,然后更改为包含Product2
的值的第一行,然后再次包含Product1
的值,然后再次为Product2
' s之后,出现带有Product1
的第二行,然后更改为包含Product2
值的第二行,然后再次包含Product1
的值,然后再次包含Product2
的值。因此,有两个乘积和两行,在此代码中,值被更改了两次,但最后该表仅包含
Product2
的值。如果break;
未注释,则Product1
的值在第一行中输出两次,然后在第二行中,则表仅包含这些Product1
的值。我知道为什么会这样。但是我还没有弄清楚如何做出正确的输出。如果有人可以告诉我如何进行正确的输出,或者提供一个示例(或者告诉我哪一部分,例如小部件用法非常错误),那就太好了。
最佳答案
代码的问题是,您的ProductListView.ui.xml中确实没有真正的表。
当然,如果从服务器检索到两个记录,则此部分代码将被调用两次:
getView().getNameLabel().setText(product.getName());
getView().getCompanyLabel().setText(product.getCompany());
getView().getSerialLabel().setText(product.getSerialNumber());
getView().getPricesLabel().setText(priceSb.toString());
第二个调用将覆盖第一个调用的值。
改善代码的要点:
您可能需要阅读有关CellTable的信息,以用于创建真实的表格视图。
不要将PresenterWidget本身用作数据持有人,而是创建
DTO,该DTO将传递到数据库并使用它来检索
数据。