2016-06-20 3 views
0

Я хотел бы привязать колонку количества к столбцам цены и количества, чтобы каждый раз, когда количество или цена, количество обновлений.Связать столбец для умножения других столбцов

import javafx.application.Application; 
    import javafx.collections.FXCollections; 
    import javafx.collections.ObservableList; 
    import javafx.event.EventHandler; 
    import javafx.geometry.Insets; 
    import javafx.scene.Group; 
    import javafx.scene.Scene; 
    import javafx.scene.control.Label; 
    import javafx.scene.control.TableColumn; 
    import javafx.scene.control.TableColumn.CellEditEvent; 
    import javafx.scene.control.TableView; 
    import javafx.scene.control.cell.PropertyValueFactory; 
    import javafx.scene.control.cell.TextFieldTableCell; 
    import javafx.scene.layout.HBox; 
    import javafx.scene.layout.VBox; 
    import javafx.scene.text.Font; 
    import javafx.stage.Stage; 
    import javafx.util.converter.NumberStringConverter; 

    /** 
    * 
    * @author Yunus 
    */ 
public class ColumnBinding extends Application{ 
    private TableView<Product> table = new TableView<Product>(); 
    private final ObservableList<Product> data = FXCollections.observableArrayList(); 
    final HBox hb = new HBox(); 

public static void main(String[] args) { 
    launch(args); 
} 

@Override 
public void start(Stage primaryStage) throws Exception { 
    Scene scene = new Scene(new Group()); 
    primaryStage.setTitle("Book Store Sample"); 
    primaryStage.setWidth(650); 
    primaryStage.setHeight(550); 

    final Label label = new Label("Testing"); 
    label.setFont(new Font("Arial", 20)); 

    table.setEditable(true); 

    TableColumn priceCol = new TableColumn("Price"); 
    priceCol.setMinWidth(100); 
    priceCol.setCellValueFactory(
      new PropertyValueFactory<Product, String>("price")); 
    priceCol.setCellFactory(TextFieldTableCell.<Product, Number>forTableColumn(new NumberStringConverter())); 
    priceCol.setOnEditCommit(
      new EventHandler<CellEditEvent<Product, Number>>() { 
       @Override 
       public void handle(CellEditEvent<Product, Number> t) { 
        ((Product) t.getTableView().getItems().get(
          t.getTablePosition().getRow()) 
        ).setPrice(t.getNewValue().intValue()); 
       } 
      } 
    ); 

    TableColumn quantityCol = new TableColumn("Quantity"); 
    quantityCol.setMinWidth(200); 
    quantityCol.setCellValueFactory(
      new PropertyValueFactory<Product, Number>("quantity")); 
    quantityCol.setCellFactory(TextFieldTableCell.<Product, Number>forTableColumn(new NumberStringConverter())); 
    quantityCol.setOnEditCommit(
      new EventHandler<CellEditEvent<Product, Number>>() { 
       @Override 
       public void handle(CellEditEvent<Product, Number> t) { 
        ((Product) t.getTableView().getItems().get(
          t.getTablePosition().getRow()) 
        ).setQuantity(t.getNewValue().intValue()); 
       } 
      } 
    ); 

    TableColumn amount = new TableColumn("Amount"); 
    amount.setMinWidth(200); 
    amount.setCellValueFactory(
      new PropertyValueFactory<Product, String>("amount")); 

    data.addAll(new Product(10, 12, 120), 
       new Product(20, 12, 240), 
       new Product(30, 12, 360), 
       new Product(40, 12, 480), 
       new Product(50, 12, 600)); 
    table.setItems(data); 
    table.getColumns().addAll(priceCol, quantityCol, amount); 
    final VBox vbox = new VBox(); 
    vbox.setSpacing(5); 
    vbox.setPadding(new Insets(10, 0, 0, 10)); 
    vbox.getChildren().addAll(label, table, hb); 

    ((Group) scene.getRoot()).getChildren().addAll(vbox); 
    primaryStage.setScene(scene); 
    primaryStage.show(); 
} 

public static class Product{ 
    Product(){} 

    public Product(float quantity, float price, float amount) { 
     this.quantity = quantity; 
     this.price = price; 
     this.amount = amount; 
    } 

    private float quantity; 
    private float price; 
    private float amount; 

    public float getQuantity() { 
     return quantity; 
    } 

    public void setQuantity(float quantity) { 
     this.quantity = quantity; 
    } 

    public float getPrice() { 
     return price; 
    } 

    public void setPrice(float price) { 
     this.price = price; 
    } 

    public float getAmount() { 
     return amount; 
    } 

    public void setAmount(float amount) { 
     this.amount = amount; 
    } 


} 
} 

задача, хотя это не изменить класс POJO (Product) с полями свойств

+1

«Задача, хотя это не изменить класс POJO с полем свойств». Зачем? Зачем ограничивать себя использованием API, специально предназначенного для вашей цели? –

+0

Потому что мне придется изменить многие другие места в исходном коде, я думаю, поскольку я использую конструктор без параметров, а значения свойств нужно инициализировать на конструкторе –

+0

Зачем вам нужно что-то менять? Единственные общедоступные методы все равно будут существовать и будут иметь точно такую ​​же функциональность (что является своеобразным моментом разработки шаблона JavaFX Property). –

ответ

2

Я бы просто использовать свойства JavaFX в классе модели. После этого вы можете установить связь путем связывания в модели:

public static class Product{ 

    private final FloatProperty quantity = new SimpleFloatProperty(); 
    private final FloatProperty price = new SimpleFloatProperty(); 
    private final ReadOnlyFloatWrapper amount = new ReadOnlyFloatWrapper(); 

    Product(){ 
     this(0f, 0f); 
    } 

    // if amount is supposed to depend on quantity and price, it makes 
    // no sense at all to have a constructor taking parameters for all 
    // three values... 
    public Product(float quantity, float price) { 
     setQuantity(quantity); 
     setPrice(price); 
     this.amount.bind(this.quantity.multiply(this.price)); 
    } 

    public float getQuantity() { 
     return quantityProperty().get(); 
    } 

    public void setQuantity(float quantity) { 
     quantityProperty().set(quantity); 
    } 

    public FloatProperty quantityProperty() { 
     return quantity ; 
    } 

    public float getPrice() { 
     return priceProperty().get(); 
    } 

    public void setPrice(float price) { 
     priceProperty().set(price); 
    } 

    public FloatProperty priceProperty() { 
     return price ; 
    } 

    public float getAmount() { 
     return amountProperty.get(); 
    } 

    // Again, it makes no sense at all to have this method 
    // if amount depends on the other values 
    // public void setAmount(float amount) { 
    //  this.amount = amount; 
    // } 

    public ReadOnlyFloatProperty amountProperty() { 
     return amount.getReadOnlyProperty(); 
    } 

} 

Теперь ваши столбцы таблицы легко:

TableColumn<Product, Float> priceColumn = new TableColumn<>("Price"); 
priceColumn.setCellValueFactory(cellData -> cellData.getValue().priceProperty().asObject()); 

TableColumn<Product, Float> quantityColumn = new TableColumn<>("Quantity"); 
quantityColumn.setCellValueFactory(cellData -> cellData.getValue().quantityProperty().asObject()); 

TableColumn<Product, Float> amountColumn = new TableColumn<>("Amount"); 
amountColumn.setCellValueFactory(cellData -> cellData.getValue().amountProperty().asObject()); 
+0

Ты потрясающий. –

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