2012-12-13 456 views
1

JavaFX2教程有一個地址簿示例,它是一個表格視圖。爲什麼我的表視圖代碼中的JavaFX2.2按鈕不可見?

教程: http://docs.oracle.com/javafx/2/fxml_get_started/fxml_tutorial_intermediate.htm#CACFEHBI

增強編輯細胞: http://docs.oracle.com/javafx/2/ui_controls/table-view.htm

修改添加複選框: http://download.oracle.com/otndocs/products/javafx/2.2/samples/Ensemble/index.html#SAMPLES/Controls/Table/Table細胞工廠

輸入在文本框中的數據,然後點擊添加按鈕添加一行到桌上。 但是,行不能被刪除。 我試圖看看是否可以在每個單元格中添加一個刪除按鈕 - 單擊它將刪除該行。 我修改了現有的示例代碼。 不知何故,按鈕不可見。任何指針讚賞。

//FXML_tableview.fxml文件

<?import javafx.collections.*?> 
<?import javafx.geometry.Insets?> 
<?import java.lang.*?> 
<?import javafx.scene.*?> 
<?import javafx.scene.control.*?> 
<?import javafx.scene.control.cell.*?> 
<?import javafx.scene.layout.*?> 
<?import fxmltableview.*?> 
<Scene fx:id="root" width="550" height="550" 
    fx:controller="fxmltableview.FXMLTableViewController" 
    xmlns:fx="http://javafx.com/fxml">  
    <GridPane alignment="center" hgap="10" vgap="10"> 
     <padding> 
      <Insets top="10" right="10" bottom="10" left="10"/> 
     </padding> 

     <TableView fx:id="tableView" GridPane.columnIndex="0" 
        GridPane.rowIndex="1"> 
     </TableView> 

     <HBox spacing="10" alignment="bottom_right" GridPane.columnIndex="0" 
       GridPane.rowIndex="2"> 
      <TextField fx:id="firstNameField" promptText="First Name" 
         prefWidth="90"/> 
      <TextField fx:id="lastNameField" promptText="Last Name" 
         prefWidth="90"/> 
      <TextField fx:id="emailField" promptText="Email" 
         prefWidth="150"/> 
      <Button text="Add" onAction="#addPerson"/> 
     </HBox> 
    </GridPane> 
</Scene> 

// FXMLTableView.java

package fxmltableview; 

import javafx.application.Application; 
import javafx.event.EventHandler; 
import javafx.fxml.FXMLLoader; 
import javafx.scene.Scene; 
import javafx.scene.control.TableColumn; 
import javafx.stage.Stage; 
import javafx.beans.property.BooleanProperty; 
import javafx.beans.property.SimpleBooleanProperty; 
import javafx.beans.property.StringProperty; 
import javafx.beans.property.SimpleStringProperty; 
import javafx.beans.value.ChangeListener; 
import javafx.beans.value.ObservableValue; 
import javafx.collections.FXCollections; 
import javafx.collections.ObservableList; 
import javafx.event.ActionEvent; 
import javafx.event.EventHandler; 
import javafx.fxml.FXML; 
import javafx.geometry.Pos; 
import javafx.scene.control.Button; 
import javafx.scene.control.CheckBox; 
import javafx.scene.control.TableCell; 
import javafx.scene.control.TableColumn; 
import javafx.scene.control.TableColumn.CellEditEvent; 
import javafx.scene.control.TableView; 
import javafx.scene.control.TextField; 
import javafx.scene.control.cell.PropertyValueFactory; 
import javafx.scene.input.KeyCode; 
import javafx.scene.input.KeyEvent; 
import javafx.scene.layout.AnchorPane; 
import javafx.util.Callback; 

public class FXMLTableView extends Application { 
    static public ObservableList<Person> data; 
    @FXML Scene root; 
    @FXML TableView tableView; 
    @Override 
    public void start(Stage primaryStage) throws Exception { 

     primaryStage.setTitle("FXML TableView Example"); 
     root = (Scene)FXMLLoader.load(getClass().getResource("fxml_tableview.fxml")); 
     primaryStage.setScene(root); 
       data = FXCollections.observableArrayList(
       new Person(true, "Jacob", "Smith", "[email protected]"), 
       new Person(false, "Isabella", "Johnson", "[email protected]"), 
       new Person(true, "Ethan", "Williams", "[email protected]"), 
       new Person(true, "Emma", "Jones", "[email protected]"), 
       new Person(false, "Michael", "Brown", "[email protected]")); 

     tableView = (TableView) root.lookup("#tableView"); 
     TableColumn delCol = new TableColumn<Person, Boolean>(); 
     delCol.setMinWidth(50); 
     delCol.setCellFactory(new Callback<TableColumn<Person, Boolean>, TableCell<Person, Boolean>>() { 

      public TableCell<Person, Boolean> call(TableColumn<Person, Boolean> p) { 
       return new DeleteTableCell<Person, Boolean>(); 
      } 
     }); 
     //"Invited" column 
     TableColumn invitedCol = new TableColumn<Person, Boolean>(); 
     invitedCol.setText("Invited"); 
     invitedCol.setMinWidth(50); 
     invitedCol.setCellValueFactory(new PropertyValueFactory("invited")); 
     invitedCol.setCellFactory(new Callback<TableColumn<Person, Boolean>, TableCell<Person, Boolean>>() { 

      public TableCell<Person, Boolean> call(TableColumn<Person, Boolean> p) { 
       return new CheckBoxTableCell<Person, Boolean>(); 
      } 
     }); 
     //"First Name" column 
     TableColumn firstNameCol = new TableColumn(); 
     firstNameCol.setText("First"); 
     firstNameCol.setCellValueFactory(new PropertyValueFactory("firstName")); 
     //"Last Name" column 
     TableColumn lastNameCol = new TableColumn(); 
     lastNameCol.setText("Last"); 
     lastNameCol.setCellValueFactory(new PropertyValueFactory("lastName")); 
     //"Email" column 
     TableColumn emailCol = new TableColumn(); 
     emailCol.setText("Email"); 
     emailCol.setMinWidth(200); 
     emailCol.setCellValueFactory(new PropertyValueFactory("email")); 

     //Set cell factory for cells that allow editing 
     Callback<TableColumn, TableCell> cellFactory = 
       new Callback<TableColumn, TableCell>() { 

        public TableCell call(TableColumn p) { 
         return new EditingCell(); 
        } 
       }; 
     emailCol.setCellFactory(cellFactory); 
     firstNameCol.setCellFactory(cellFactory); 
     lastNameCol.setCellFactory(cellFactory); 

     //Set handler to update ObservableList properties. Applicable if cell is edited 
     updateObservableListProperties(emailCol, firstNameCol, lastNameCol); 


     tableView.setItems(data); 
     //Enabling editing 
     tableView.setEditable(true); 
     tableView.getColumns().addAll(invitedCol, firstNameCol, lastNameCol, emailCol, delCol); 
//  root.getChildren().add(tableView); 
     primaryStage.show(); 
    } 
    private void updateObservableListProperties(TableColumn emailCol, TableColumn firstNameCol, 
      TableColumn lastNameCol) { 
     //Modifying the email property in the ObservableList 
     emailCol.setOnEditCommit(new EventHandler<TableColumn.CellEditEvent<Person, String>>() {   
      @Override public void handle(TableColumn.CellEditEvent<Person, String> t) { 
       ((Person) t.getTableView().getItems().get(
         t.getTablePosition().getRow())).setEmail(t.getNewValue()); 
      } 
     }); 
     //Modifying the firstName property in the ObservableList 
     firstNameCol.setOnEditCommit(new EventHandler<TableColumn.CellEditEvent<Person, String>>() {   
      @Override public void handle(TableColumn.CellEditEvent<Person, String> t) { 
       ((Person) t.getTableView().getItems().get(
         t.getTablePosition().getRow())).setFirstName(t.getNewValue()); 
      } 
     }); 
     //Modifying the lastName property in the ObservableList 
     lastNameCol.setOnEditCommit(new EventHandler<TableColumn.CellEditEvent<Person, String>>() {   
      @Override public void handle(TableColumn.CellEditEvent<Person, String> t) { 
       ((Person) t.getTableView().getItems().get(
         t.getTablePosition().getRow())).setLastName(t.getNewValue()); 
      } 
     }); 
    } 
    //CheckBoxTableCell for creating a CheckBox in a table cell 
    public static class CheckBoxTableCell<S, T> extends TableCell<S, T> { 
     private final CheckBox checkBox; 
     private ObservableValue<T> ov; 

     public CheckBoxTableCell() { 
      this.checkBox = new CheckBox(); 
      this.checkBox.setAlignment(Pos.CENTER); 

      setAlignment(Pos.CENTER); 
      setGraphic(checkBox); 
     } 

     @Override public void updateItem(T item, boolean empty) { 
      super.updateItem(item, empty); 
      if (empty) { 
       setText(null); 
       setGraphic(null); 
      } else { 
       setGraphic(checkBox); 
       if (ov instanceof BooleanProperty) { 
        checkBox.selectedProperty().unbindBidirectional((BooleanProperty) ov); 
       } 
       ov = getTableColumn().getCellObservableValue(getIndex()); 
       if (ov instanceof BooleanProperty) { 
        checkBox.selectedProperty().bindBidirectional((BooleanProperty) ov); 
       } 
      } 
     } 
    } 
    public static class DeleteTableCell<S, T> extends TableCell<S, T> { 
     private final Button del; 
     private ObservableValue<T> ov; 

     public DeleteTableCell() { 
      this.del = new Button("X"); 
      del.setStyle("-fx-base: red;"); 
      this.del.setAlignment(Pos.CENTER); 

      setAlignment(Pos.CENTER); 
      setGraphic(del); 
      del.setOnAction(new EventHandler<ActionEvent>() { 
       @Override 
       public void handle(ActionEvent t) { 
        int i= getIndex(); 
        FXMLTableView.data.remove(i); 
       }     
      }); 
     } 

     @Override public void updateItem(T item, boolean empty) { 
      super.updateItem(item, empty); 
      if (empty) { 
       setText(null); 
       setGraphic(null); 
      } else { 
       setGraphic(del); 
      } 
     } 
    } 
    // EditingCell - for editing capability in a TableCell 
    public static class EditingCell extends TableCell<Person, String> { 
     private TextField textField; 

     public EditingCell() { 
     } 

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

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

     private void createTextField() { 
      textField = new TextField(getString()); 
      textField.setMinWidth(this.getWidth() - this.getGraphicTextGap() * 2); 
      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(); 
     } 
    } 

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

// FXMLTableViewController.java

package fxmltableview; 

import javafx.collections.ObservableList; 
import javafx.event.ActionEvent; 
import javafx.event.EventHandler; 
import javafx.fxml.FXML; 
import javafx.scene.control.TableColumn; 
import javafx.scene.control.TableView; 
import javafx.scene.control.TextField; 

public class FXMLTableViewController { 
    @FXML private TableView<Person> tableView; 
    @FXML private TextField firstNameField; 
    @FXML private TextField lastNameField; 
    @FXML private TextField emailField; 

    @FXML 
    protected void addPerson(ActionEvent event) { 
     ObservableList<Person> data = tableView.getItems(); 
     data.add(new Person(false, firstNameField.getText(), 
      lastNameField.getText(), 
      emailField.getText() 
     )); 

     firstNameField.setText(""); 
     lastNameField.setText(""); 
     emailField.setText(""); 
    } 


} 

// Person.java

package fxmltableview; 

import javafx.beans.property.BooleanProperty; 
import javafx.beans.property.SimpleBooleanProperty; 
import javafx.beans.property.SimpleStringProperty; 
import javafx.beans.property.StringProperty; 
import javafx.beans.value.ChangeListener; 
import javafx.beans.value.ObservableValue; 

//Person object 
public class Person { 
    private BooleanProperty invited; 
    private StringProperty firstName; 
    private StringProperty lastName; 
    private StringProperty email; 

    Person(boolean invited, String fName, String lName, String email) { 
     this.invited = new SimpleBooleanProperty(invited); 
     this.firstName = new SimpleStringProperty(fName); 
     this.lastName = new SimpleStringProperty(lName); 
     this.email = new SimpleStringProperty(email); 
     this.invited = new SimpleBooleanProperty(invited); 

     this.invited.addListener(new ChangeListener<Boolean>() { 
      public void changed(ObservableValue<? extends Boolean> ov, Boolean t, Boolean t1) { 
       System.out.println(firstNameProperty().get() + " invited: " + t1); 
      } 
     });    
    } 

    public BooleanProperty invitedProperty() { return invited; } 

    public StringProperty firstNameProperty() { return firstName; } 

    public StringProperty lastNameProperty() { return lastName; } 

    public StringProperty emailProperty() { return email; } 

    public void setLastName(String lastName) { this.lastName.set(lastName); } 

    public void setFirstName(String firstName) { this.firstName.set(firstName); } 

    public void setEmail(String email) { this.email.set(email); } 
} 

回答

1

delCol的單元格值工廠缺失。 Add

delCol.setCellValueFactory(new PropertyValueFactory("invited")); 

PropertyValueFactory的參數在這裏並不重要。

+0

是的,我也意識到了。 http://docs.oracle.com/javafx/2/api/javafx/scene/control/cell/PropertyValueFactory.html – likejiujitsu

相關問題