【发布时间】:2018-09-10 14:06:57
【问题描述】:
我一直在处理与 listcell 编辑有关的问题。到目前为止,我已经成功地为 ListCells 创建了 ContextMenu,但是随着我的进步,我遇到了一个问题。我的整个想法是,例如,当我单击菜单按钮 Edit 时,我想编辑选定的 ListCell,但不是那种像 listview 提供的 edit() 方法那样的编辑。这个不同。我尝试创建自定义 TextFieldListCell 类,以便我可以使用自己的规则验证文本字段,但我没有成功。
这里是我的带有菜单项的列表视图单元工厂的代码供参考:
languages.setEditable(true);
languages.setCellFactory(ev -> {
ListCell<String> cell = new ListCell<>();
ContextMenu contextMenu = new ContextMenu();
MenuItem editItem = new MenuItem();
editItem.textProperty().bind(Bindings.format("Edit \"%s\"", cell.itemProperty()));
editItem.setOnAction(event -> {
// The LanguageListCell class i want to put here...
});
MenuItem addItem = new MenuItem("Add language");
addItem.setOnAction(event -> {
String item = "";
languages.getItems().add(item);
});
MenuItem deleteItem = new MenuItem();
deleteItem.textProperty().bind(Bindings.format("Delete \"%s\"", cell.itemProperty()));
deleteItem.setOnAction(event -> languages.getItems().remove(cell.getItem()));
contextMenu.getItems().addAll(addItem, editItem, deleteItem);
cell.textProperty().bind(cell.itemProperty());
cell.emptyProperty().addListener((obs, wasEmpty, isNowEmpty) -> {
if (isNowEmpty) {
cell.setContextMenu(null);
} else {
cell.setContextMenu(contextMenu);
}
});
return cell ;
});
这是我的自定义 TextFieldListCell 类的代码:
public class LanguageListCell extends ListCell<String>
{
private TextField textField;
public LanguageListCell()
{
}
@Override
public void startEdit() {
super.startEdit();
if (textField == null) {
createTextField();
}
setText(null);
setGraphic(textField);
textField.selectAll();
}
@Override
public void cancelEdit() {
super.cancelEdit();
setText((String) getItem());
setGraphic(getGraphic());
}
@Override
public void updateItem(String item, boolean empty) {
super.updateItem(item, empty);
if (empty) {
setText(null);
setGraphic(null);
} else {
if (isEditing()) {
if (textField != null) {
textField.setText(getString());
}
setText(null);
setGraphic(textField);
} else {
setText(getString());
setGraphic(getGraphic());
}
}
}
private void createTextField() {
textField = new TextField(getString());
textField.setOnKeyReleased(new EventHandler<KeyEvent>() {
@Override
public void handle(KeyEvent t) {
if (t.getCode() == KeyCode.ENTER) {
commitEdit(textField.getText());
} else if (t.getCode() == KeyCode.ESCAPE) {
cancelEdit();
}
}
});
}
private String getString() {
return getItem() == null ? "" : getItem().toString();
}
}
【问题讨论】:
-
setGraphic(getGraphic());如果您想保持图形不变(即在取消编辑后继续显示文本字段),这是正确的做法。实际上使用您的自定义单元格而不是ListCell也是一个好主意...ev.edit(cell.getIndex())将是使ListView顺便编辑单元格的适当代码。 -
使用 edit() 的问题是它调用了默认的 TextFieldListCell 类,我不能使用我的自定义类。 @fabian
-
如果它使用默认的
TextFieldListCell,那么您就没有使用cellValueFactory来返回您的自定义单元格。 -
使用
cellFactory,您发布的单元格根本不应该是可编辑的。 -
是的,现在我明白了。我会弄清楚。感谢您的帮助!
标签: java listview javafx textfield