我有一个包含几个子编辑器的 ValueAwareEditor:
本质上,OfferDto 由 TariffDto 和 Commission 组成。委员会可以是 4 种子类型之一,但只有一种。通常,TariffDto 中可能的佣金列表仅包含一个元素,但有时可以包含两个元素。
public class OfferDto
{
private TariffDto tariff;
// selected from the list in the tariff
private Commission commission;
}
public class TariffDto extends EntityDto
{
// omitted for brevity...
protected List<Commission> commissions = new ArrayList<Commission>();
}
当佣金包含多个项目时,我想显示一个包含两个选项的下拉列表,并添加允许用户在它们之间进行选择,每次在 OfferDto 和 CommissionEditor 中重置佣金。
问题是,当第二次调用commission.setValue() 时,编辑器没有改变。我应该在这里做什么?
public class OfferEditor extends Composite implements ValueAwareEditor<OfferDto>
{
@UiField
TariffRenderer tariff;
@Ignore
@UiField
HTMLPanel panel;
@UiField
CommissionEditor commission;
@Override
public void setValue(final OfferDto value)
{
panel.clear();
List<Commission> commissions = value.getTariff().getCommissions();
if(commissions.size() == 1)
{
value.setCommission(commissions.get(0));
}
else
{
// multiple commissions
ValueListBox<Commission> dropdown = new ValueListBox<Commission>(new Renderer<Commission>()
{
@Override
public String render(Commission object)
{
return object == null ? "" : object.getName();
}
@Override
public void render(Commission object, Appendable appendable) throws IOException
{
appendable.append(render(object));
}
});
dropdown.setValue(value.getCommission());
dropdown.setAcceptableValues(commissions);
dropdown.addValueChangeHandler(new ValueChangeHandler<Commission>()
{
@Override
public void onValueChange(ValueChangeEvent<Commission> event)
{
Commission selected = event.getValue();
// this works, but the CommissionEditor that was first rendered remains
value.setCommission(selected);
}
});
panel.add(dropdown);
}
}
}
目前,我在 ValueListBox 中呈现佣金列表,然后当值更改时,我将该值推送到 OfferDto。委员会似乎设置正确,但 subEditor 没有改变。
非常感谢任何帮助。
编辑:
CommissionEditor 根据类型显示相关的子编辑器。
public class CommissionEditor extends Composite implements Editor<Commission>
{
private static CommissionEditorUiBinder uiBinder = GWT.create(CommissionEditorUiBinder.class);
interface CommissionEditorUiBinder extends UiBinder<Widget, CommissionEditor>
{
}
@UiField
Panel subEditorPanel;
public CommissionEditor()
{
initWidget(uiBinder.createAndBindUi(this));
}
@Ignore
final UnitRateCommissionEditor unitRateCommissionEditor = new UnitRateCommissionEditor();
@Path("")
final AbstractSubTypeEditor<Commission, UnitRateCommission, UnitRateCommissionEditor> unitRateCommissionEditorWrapper = new AbstractSubTypeEditor<Commission, UnitRateCommission, UnitRateCommissionEditor>(
unitRateCommissionEditor)
{
@Override
public void setValue(final Commission value)
{
if(value instanceof UnitRateCommission)
{
setValue(value, value instanceof UnitRateCommission);
System.out.println("UnitRateCommission setValue");
subEditorPanel.clear();
subEditorPanel.add(unitRateCommissionEditor);
}
}
};
@Ignore
final StandingChargeCommissionEditor standingChargeCommissionEditor = new StandingChargeCommissionEditor();
@Path("")
final AbstractSubTypeEditor<Commission, StandingChargeCommission, StandingChargeCommissionEditor> standingChargeCommissionEditorWrapper = new AbstractSubTypeEditor<Commission, StandingChargeCommission, StandingChargeCommissionEditor>(
standingChargeCommissionEditor)
{
@Override
public void setValue(final Commission value)
{
if(value instanceof StandingChargeCommission)
{
setValue(value, value instanceof StandingChargeCommission);
System.out.println("StandingChargeCommission setValue");
subEditorPanel.clear();
subEditorPanel.add(standingChargeCommissionEditor);
}
}
};
@Ignore
final PerMwhCommissionEditor perMwhCommissionEditor = new PerMwhCommissionEditor();
@Path("")
final AbstractSubTypeEditor<Commission, PerMwhCommission, PerMwhCommissionEditor> perMwhCommissionEditorWrapper = new AbstractSubTypeEditor<Commission, PerMwhCommission, PerMwhCommissionEditor>(
perMwhCommissionEditor)
{
@Override
public void setValue(final Commission value)
{
if(value instanceof PerMwhCommission)
{
setValue(value, value instanceof PerMwhCommission);
System.out.println("PerMwhCommission setValue");
subEditorPanel.clear();
subEditorPanel.add(perMwhCommissionEditor);
}
}
};
}
可能的解决方案:
我OfferEditor
是这样改的:
public class OfferEditor extends Composite implements Editor<OfferDto>
{
@UiField
TariffRenderer tariff;
@Path("tariff.commissions")
@UiField
CommissionsEditor commission;
}
新编辑器CommissionsEditor
是 CompositeEditor。它需要获取 List duty.commissions 并将选择的 Commission 设置为 offer.commission:
public class CommissionsEditor extends Composite implements CompositeEditor<List<Commission>, Commission, CommissionEditor>
{
private static CommissionsEditorUiBinder uiBinder = GWT.create(CommissionsEditorUiBinder.class);
interface CommissionsEditorUiBinder extends UiBinder<Widget, CommissionsEditor>
{
}
private EditorChain<Commission, CommissionEditor> chain;
@UiField
FlowPanel dropdownPanel, subEditorPanel;
@Ignore
CommissionEditor subEditor;
public CommissionsEditor()
{
initWidget(uiBinder.createAndBindUi(this));
}
@Override
public void setValue(List<Commission> valueList)
{
// clear both panels
dropdownPanel.clear();
subEditorPanel.clear();
if(valueList.size() == 1)
{
// set the commission to the first in the list
Commission selected = valueList.get(0);
subEditor = new CommissionEditor();
subEditorPanel.add(subEditor);
chain.attach(selected, subEditor);
}
else if(valueList.size() > 1)
{
ValueListBox<Commission> dropdown = new ValueListBox<Commission>(new Renderer<Commission>()
{
@Override
public String render(Commission object)
{
return object == null ? "" : object.getName();
}
@Override
public void render(Commission object, Appendable appendable) throws IOException
{
appendable.append(render(object));
}
});
dropdownPanel.add(dropdown);
dropdown.setValue(valueList.get(0));
dropdown.setAcceptableValues(valueList);
dropdown.addValueChangeHandler(new ValueChangeHandler<Commission>()
{
@Override
public void onValueChange(ValueChangeEvent<Commission> event)
{
Commission selected = event.getValue();
subEditorPanel.clear();
CommissionEditor subEditor = new CommissionEditor();
subEditorPanel.add(subEditor);
chain.attach(selected, subEditor);
}
});
}
}
@Override
public void flush()
{
}
@Override
public void onPropertyChange(String... paths)
{
// TODO Auto-generated method stub
}
@Override
public void setDelegate(EditorDelegate<List<Commission>> delegate)
{
// TODO Auto-generated method stub
}
@Override
public CommissionEditor createEditorForTraversal()
{
return new CommissionEditor();
}
@Override
public String getPathElement(CommissionEditor subEditor)
{
return null;
}
@Override
public void setEditorChain(EditorChain<Commission, CommissionEditor> chain)
{
this.chain = chain;
}
}
当CommissionsEditor
渲染下拉菜单并被onValueChange()
调用时,新编辑器被创建,但佣金的值似乎从未被设置。
由于某种原因,选定的 subEditor 的值没有被推入offer.setCommission()
. 我以为chain.attach()
会为我执行此操作?