0

我有一个包含几个子编辑器的 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()会为我执行此操作?

4

0 回答 0