2013-11-16 2 views
7

У меня есть элемент управления TableView, который состоит из нескольких столбцов, содержащих разные типы, включая String s и Number s. Я пытаюсь написать подходящую функцию обратного вызова для редактируемой ячейки Number, но я не могу ее никуда с ней, так как получаю множество проблем, начиная от пустых ячеек и заканчивая исключениями.Редактирование ячейки Number в TableView

Я прочитал http://docs.oracle.com/javafx/2/ui_controls/table-view.htm, но это касается только значений строк в ячейках. Точка прилипания, кажется, lastNameCol.setCellFactory(TextFieldTableCell.forTableColumn());. Эта строка, по-видимому, предназначена для полей «Текст», а не для полей «Число».

Кроме того, я хочу выполнить проверку введенных чисел. Для этого требуется специальный обратный вызов для CellFactory для этого? Если да, как я могу разработать обратный вызов, который принимает типы номеров и проверяет их?

Вот фрагмент кода, что я в настоящее время в моем проекте:

@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()); 
     } 
    }); 
} 

Спасибо за любую помощь заранее.

ответ

12

TextFieldTableCell тип параметризирован и имеет свойство stringConverter, которое можно использовать для преобразования в/из строки и желаемого типа.

Попробуйте что-то вроде:

TextFieldTableCell.<BMIRecord, Number>forTableColumn(new NumberStringConverter()) 

NumberStringConverter имеет некоторые дополнительные конструкторы для указания форматирования, см Javadocs.

Вот более полный пример:

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())); 

Это не работает хорошо, хотя, потому что NumberStringConverter так, чтобы быть тупым, плохо реализован, что он просто бросает ParseException на вас, если вы случайно ввести строка вместо числа в ячейке.

Однако должно быть относительно тривиально реализовать собственный преобразователь строк, где вы также можете выполнить некоторую простую проверку (например, значение должно быть от 0 до 100).

+0

Спасибо за предложение, я попробовал метод вы предложили, кроме '' часть отвергается. Без этого я получаю ошибку, аналогичную предыдущей: «Метод setCellFactory (Callback , TableCell >) в типе TableColumn не применим для аргументов (Callback , TableCell >) " – Steve

+2

Прошу прощения, моя Java немного ржавая (я использую Scala). Я исправил синтаксис. –

+0

Это сработало отлично. Спасибо, что нашли время, чтобы улучшить ответ :) – Steve

0

использовать этот

age.setCellFactory(TextFieldTableCell.forTableColumn(new IntegerStringConverter())); 

 Смежные вопросы

  • Нет связанных вопросов^_^