Java 在 TableView 中编辑数字单元格
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/20020037/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Editing a Number cell in a TableView
提问by Steve
I have a TableView
control which consists of several columns containg different types including String
s and Number
s. I have been trying to write a suitable callback function for an editable Number cell, but I can't get anywhere with it as I get a variety of issues ranging from empty cells to exceptions.
我有一个TableView
控件,它由几个包含不同类型的列组成,包括String
s 和Number
s。我一直在尝试为可编辑的 Number 单元格编写一个合适的回调函数,但是我无法使用它,因为我遇到了从空单元格到异常的各种问题。
I have read through http://docs.oracle.com/javafx/2/ui_controls/table-view.htmbut this only covers String values in cells. The sticking point seems to be lastNameCol.setCellFactory(TextFieldTableCell.forTableColumn());
. This line seems to be tailored for Text fields and not for Number fields.
我已经通读了http://docs.oracle.com/javafx/2/ui_controls/table-view.htm但这仅涵盖单元格中的字符串值。症结似乎是lastNameCol.setCellFactory(TextFieldTableCell.forTableColumn());
。这一行似乎是为文本字段而不是数字字段量身定制的。
Also, I wish to perform validation on the numbers entered. Does this require a custom callback for the CellFactory
in order to do this? If so, how can I develop a callback that accepts Number types and validates them?
另外,我希望对输入的数字进行验证。这是否需要自定义回调CellFactory
才能执行此操作?如果是这样,我如何开发一个接受 Number 类型并验证它们的回调?
Here's a code snippet of what I currently have in my project:
这是我目前在我的项目中拥有的代码片段:
@FXML private TableView<BMIRecord> fxBMITable;
@FXML private TableColumn<BMIRecord, String> fxBMITableDate;
@FXML private TableColumn<BMIRecord, String> fxBMITableTime;
@FXML private TableColumn<BMIRecord, Number> fxBMITableHeight;
@FXML private TableColumn<BMIRecord, Number> fxBMITableWeight;
@FXML private TableColumn<BMIRecord, Number> fxBMITableBMI;
// ...
private void someFunc() {
fxBMITable.setEditable(true);
/* BMI table callback configuration */
fxBMITableHeight.setCellValueFactory(new Callback<CellDataFeatures<BMIRecord, String>, ObservableValue<String>>() {
public ObservableValue<String> call(CellDataFeatures<BMIRecord, String> p) {
return new SimpleStringProperty(p.getValue().getDateString());
}
});
/*
* ERROR:
* The method setCellFactory(Callback<TableColumn<BMIRecord,Number>,TableCell<BMIRecord,Number>>)
* in the type TableColumn<BMIRecord,Number> is not applicable for the arguments
* (Callback<TableColumn<Object,String>,TableCell<Object,String>>)
*/
fxBMITableHeight.setCellFactory(TextFieldTableCell.forTableColumn());
fxBMITableHeight.setOnEditCommit(new EventHandler<CellEditEvent<BMIRecord, Number>>() {
@Override
public void handle(CellEditEvent<BMIRecord, Number> t) {
((BMIRecord)t.getTableView().getItems().get(t.getTablePosition().getRow())).setHeight(t.getNewValue().doubleValue());
}
});
}
Thanks for any help in advance.
提前感谢您的任何帮助。
采纳答案by Knut Arne Vedaa
TextFieldTableCell is type parameterized and has a stringConverter
property that you can use to convert to/from String and your desired type.
TextFieldTableCell 是类型参数化的,并且具有一个stringConverter
属性,您可以使用该属性来转换为/从字符串和所需的类型。
Try something like:
尝试类似:
TextFieldTableCell.<BMIRecord, Number>forTableColumn(new NumberStringConverter())
NumberStringConverter has some additional constructors for specifying the formatting, see the javadocs.
NumberStringConverter 有一些额外的构造函数用于指定格式,请参阅 javadocs。
Here's a more complete example:
这是一个更完整的示例:
public class Person {
public Person(String name0, int age0) {
name = name0;
age = age0;
}
public String name;
public int age;
}
TableView<Person> personTable = new TableView<>();
TableColumn<Person, Number> age = new TableColumn<>();
age.setCellValueFactory(new Callback<CellDataFeatures<Person, Number>, ObservableValue<Number>>() {
@Override
public ObservableValue<Number> call(CellDataFeatures<Person, Number> p) {
return new SimpleIntegerProperty(p.getValue().age);
}
});
age.setCellFactory(TextFieldTableCell.<Person, Number>forTableColumn(new NumberStringConverter()));
This does not work well, though, because NumberStringConverter is so, to be blunt, badly implemented that it simply throws a ParseException
at you if you happen to enter a string instead of a number in the cell.
但是,这并不能很好地工作,因为 NumberStringConverter 是这样的,坦率地说,实现得很糟糕,ParseException
如果您碰巧在单元格中输入字符串而不是数字,它只会向您抛出 a 。
However it should be relatively trivial to implement your own string converter, where you could also do some simple validation (e.g. value should be between 0 and 100).
然而,实现您自己的字符串转换器应该相对简单,您还可以在其中进行一些简单的验证(例如,值应介于 0 和 100 之间)。
回答by Zcon
use this
用这个
age.setCellFactory(TextFieldTableCell.forTableColumn(new IntegerStringConverter()));
回答by alex valuiskyi
jalvafxlibrary:
jalvafx库:
Solution prevent user from invalid input. Only 0-9, coma and point symbols are allowed. You can set minimun and maximum number value.
解决方案防止用户输入无效。只允许使用 0-9、彗形和点符号。您可以设置最小值和最大值。
Method to use signature:
签名使用方法:
TableViewUtils.setEditNumberCellFactory(
TableColumn<T, K> cell,
BiConsumer<T, Double> changeHandler,
String editControlHeader,
Double minAllowedValue,
Double maxAllowedValue,
Function<T, Boolean> ignoreEdit)
Mock table:
模拟表:
TableView<String> tableView = new TableView<>();
tableView.getItems().addAll("USA", "Canada", "Brazil");
TableColumn<String, String> country = new TableColumn<>("Country");
TableColumn<String, Integer> column = new TableColumn<>("Some value");
tableView.getColumns().add(country);
tableView.getColumns().add(column);
country.setCellValueFactory(
data -> new SimpleObjectProperty<>(data.getValue()));
column.setCellValueFactory(
data -> new SimpleObjectProperty<>(800));
Solution:
解决方案:
BiConsumer<String, Double> changeHandler = (item, newValue) -> {
System.out.println("New value is " + newValue);
// Your code
};
Function<String, Boolean> ignoreEdit = item -> item.equalsIgnoreCase("USA");
TableViewUtils.setEditNumberCellFactory(column, changeHandler, "New value:", 200.0, 800.0, ignoreEdit);