GWT CellTable和ListBoxes复杂标识符

时间:2012-03-12 16:23:08

标签: gwt listbox celltable

我正在关注如何将ListBoxes / SelectionCells添加到CellTable的Goolge示例,但我无法想象如何更改行为,因此匹配不会显示字符串值。

我显示@SelectionCell的项目不是唯一的(即可以有2个具有相同名称的元素),所以我需要使用与该对象关联的其他字段来知道选择了哪个

for (IrrigationProgramDTO program: programOptions)    
 categoryNames.add(program.getName());

SelectionCell categoryCell = new SelectionCell(categoryNames);
Column<IrrigationGapDTO, String> categoryColumn = new Column<IrrigationGapDTO, String>    (categoryCell) {
      @Override
      public String getValue(IrrigationGapDTO object) {
          if (object.getProgramSelected()!=null)
              return object.getProgramSelected().getName();
          else
              return "";
      }
    };      
    categoryColumn.setFieldUpdater(new FieldUpdater<IrrigationGapDTO, String>() {
      public void update(int index, IrrigationGapDTO object, String value) {
          for (IrrigationProgramDTO program: programOptions) {
                  //not valid as there could be more than 1 program with the same name
              if (program.getName().equals(value)) { 
                  object.setProgramSelected(program);
                  break;
              }

          }  
      }

3 个答案:

答案 0 :(得分:2)

以下是我对解决方案#3的新实施(请注意,您必须将FieldUpdater添加到列中才能使其正常工作):

import java.util.Arrays;
import java.util.List;

import com.google.gwt.cell.client.AbstractEditableCell;
import com.google.gwt.cell.client.Cell;
import com.google.gwt.cell.client.ValueUpdater;
import com.google.gwt.core.client.GWT;
import com.google.gwt.dom.client.BrowserEvents;
import com.google.gwt.dom.client.Element;
import com.google.gwt.dom.client.NativeEvent;
import com.google.gwt.dom.client.SelectElement;
import com.google.gwt.safehtml.client.SafeHtmlTemplates;
import com.google.gwt.safehtml.client.SafeHtmlTemplates.Template;
import com.google.gwt.safehtml.shared.SafeHtml;
import com.google.gwt.safehtml.shared.SafeHtmlBuilder;

/**
 * A {@link Cell} used to render a drop-down list.
 *
 * @author Gaspard van Koningsveld
 */
public class ItemSelectionCell<C> extends AbstractEditableCell<C, C> {

    interface Template extends SafeHtmlTemplates {
        @Template("<select tabindex=\"-1\" style=\"width:100%\">")
        SafeHtml beginSelect();

        @Template("<option value=\"{0}\">{1}</option>")
        SafeHtml deselected(int hash, String option);

        @Template("<option value=\"{0}\" selected=\"selected\">{1}</option>")
        SafeHtml selected(int hash, String option);

        @Template("</select>")
        SafeHtml endSelect();
    }

    private static Template template;

    private List<C> items;

    public ItemSelectionCell(C itemsArray[]) {
        this(Arrays.asList(itemsArray));
    }

    public ItemSelectionCell(List<C> items) {
        super(BrowserEvents.CHANGE);
        if (template == null) {
            template = GWT.create(Template.class);
        }
        this.items = items;
    }

    @Override
    public void onBrowserEvent(Context context, Element parent, C value, NativeEvent event, ValueUpdater<C> valueUpdater) {
        super.onBrowserEvent(context, parent, value, event, valueUpdater);
        if (BrowserEvents.CHANGE.equals(event.getType())) {
            SelectElement select = parent.getFirstChild().cast();
            int newIndex = select.getSelectedIndex();
            valueUpdater.update(items.get(newIndex));
        }
    }

    @Override
    public void render(Context context, C value, SafeHtmlBuilder sb) {
        sb.append(template.beginSelect());
        for (int i = 0; i < items.size(); i++) {
            C item = items.get(i);
            if (item.equals(value)) {
                sb.append(template.selected(i, getItemDisplayString(item)));
            } else {
                sb.append(template.deselected(i, getItemDisplayString(item)));
            }
        }
        sb.append(template.endSelect());
    }

    public String getItemDisplayString(C item) {
        return item.toString();
    }

    public List<C> getItems() {
        return items;
    }

    public void setItems(List<C> items) {
        this.items = items;
    }

    @Override
    public boolean isEditing(Context context, Element parent, C value) {
        return false;
    }
}

答案 1 :(得分:1)

3种可能的解决方案:

<强> 1。肮脏的解决方法:

而不是getName()返回getName() +一些唯一标识符:

public String getValue(IrrigationGapDTO object) {
    if (object.getProgramSelected()!=null)
        return object.getProgramSelected().getName()+"_"+object.getUniqueIdentiufier();
    else
        return "";
}

然后在FieldUpdater中你可以拆分“_”字符并处理重复

<强> 2。使用唯一ID代替getName() : 只需为您的程序生成/分配一个唯一的ID,然后使用它而不是名称。

第3。使用IrrigationProgramDTO类型代替String

您可以在列定义中使用String类,而不是IrrigationProgramDTO。但是,您可能必须使用用户定义的SelectionCell,它将IrrigationProgramDTO类型而不是String作为数据类型。

Column<IrrigationGapDTO, IrrigationProgramDTO> categoryColumn = new Column<IrrigationGapDTO, IrrigationProgramDTO>    (categoryCell) {
  @Override
  public IrrigationProgramDTO (IrrigationGapDTO object) {
      if (object.getProgramSelected()!=null)
          return object.getProgramSelected();
      else
          return null;
  }

};      
categoryColumn.setFieldUpdater(new FieldUpdater<IrrigationGapDTO, IrrigationProgramDTO>() {
  public void update(int index, IrrigationGapDTO object, IrrigationProgramDTO value) {
       object.setProgramSelected(program);
      }  
  }

答案 2 :(得分:0)

以下是我对@Ümit的解决方案#3的实施:

public static abstract class EditSelectColumn<E, S> {

    Map<String, S> selectionMap = new HashMap<String, S>();

    EditColumn<E> column;

    protected final String relationshipFieldName;

    public EditSelectColumn(String relationshipFieldName) {
        this.relationshipFieldName = relationshipFieldName;

        for (S option : getOptions()) {
            assert getOptionString(option) != null : "Option string cannot be null, please check your database";
            selectionMap.put(getOptionString(option), option);
        }
        SelectionCell cell = new SelectionCell(new ArrayList<String>(selectionMap.keySet()));
        column = new EditColumn<E>(cell) {
            @Override
            public String getValue(E object) {
                if (getOption(object) == null)
                    return "";
                return getOptionString(getOption(object));
            }

            @Override
            public void setValue(E object, String value) {
                setOption(object, selectionMap.get(value));
            }
        };
    }

    public EditColumn<E> getColumn() {
        return column;
    }

    public abstract List<S> getOptions();

    public abstract String getOptionString(S option);

    public abstract S getOption(E object);

    public abstract void setOption(E object, S value);
}