2013-10-04 12 views
5

के साथ रिक्त पंक्तियों में सामग्री दिखाई देती है यदि नीचे value.setCellFactory(NUMBER_CELL_FACTORY); पर टिप्पणी की गई है तो नीचे दिया गया प्रोग्राम ठीक काम करता है।कस्टम सेल फैक्ट्री

यदि यह शामिल है, तो तालिका दृश्य अजीब तरीके से व्यवहार करता है * - यदि आप बस कोड कॉपी करते हैं, इसे लॉन्च करते हैं और + बटन पर कुछ बार क्लिक करते हैं, तो आप तालिका के नीचे खाली पंक्तियों में दिखाई देने वाली सामग्री देखेंगे।

क्या मुझे कुछ याद आ रही है?

* जावाएफएक्स 8 - बी 106 पर परीक्षण किया गया।

import javafx.application.Application; 
import javafx.beans.property.DoubleProperty; 
import javafx.beans.property.SimpleDoubleProperty; 
import javafx.scene.Scene; 
import javafx.scene.control.Button; 
import javafx.scene.control.TableCell; 
import javafx.scene.control.TableColumn; 
import javafx.scene.control.TableView; 
import javafx.scene.control.cell.PropertyValueFactory; 
import javafx.scene.layout.AnchorPane; 
import javafx.scene.layout.VBox; 
import javafx.scene.paint.Color; 
import javafx.stage.Stage; 
import javafx.util.Callback; 

public class TestFX extends Application { 

    @Override 
    public void start(final Stage stage) throws Exception { 
     MyTable table = new MyTable(); 

     Scene scene = new Scene(table); 

     stage.setScene(scene); 
     stage.show(); 
    } 

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

    static class MyTable extends AnchorPane { 

     private static final Callback NUMBER_CELL_FACTORY = (p) -> new NumberTableCell<>(); 

     private final Button addRow = new Button("+"); 
     private final TableView<Item> table = new TableView<>(); 

     MyTable() { 
      super(); 
      initTableView(); 
      addRow.setOnMouseClicked((e) -> addItem()); 
      VBox vbox = new VBox(); 
      vbox.getChildren().addAll(addRow, table); 
      getChildren().add(vbox); 
     } 

     public void addItem() { 
      table.getItems().addAll(new Item()); 
     } 

     private void initTableView() { 
      TableColumn<Item, Double> value = new TableColumn<>("Value"); 
      value.setCellValueFactory(new PropertyValueFactory<>("value")); 
      value.setCellFactory(NUMBER_CELL_FACTORY); 

      table.getColumns().add(value); 
      table.setColumnResizePolicy(TableView.CONSTRAINED_RESIZE_POLICY); 
     } 
    } 

    public static class Item { 
     private final DoubleProperty value = new SimpleDoubleProperty(); 

     public DoubleProperty valueProperty() { 
      return value; 
     } 
    } 

    static class NumberTableCell<T> extends TableCell<T, Double> { 
     private final Color fill = Color.LIGHTGREY; 

     @Override 
     protected void updateItem(Double item, boolean empty) { 
      super.updateItem(item, empty); 
      if (empty) return; 
      setText(String.valueOf(item)); 
      setTextFill(fill); 
     } 
    } 
} 

उत्तर

6

मैं Win7 Java7b108 पर अपने नमूना कार्यक्रम की कोशिश की और यह NumberTableCell के साथ ठीक काम करने के लिए लग रहा था, फिर भी यह अभी भी एक मुद्दा है।

समस्या यह है कि कोशिकाओं का पुन: उपयोग किया जाता है, इसलिए यदि किसी भी कारण से कोई सेल खाली हो जाता है, तो आपको सेल में सेट किए गए किसी भी कस्टम मान को साफ़ करने की आवश्यकता होती है ताकि यह एक डिफ़ॉल्ट खाली सेल की तरह प्रस्तुत हो। नीचे दिए गए कोड को दर्शाता है ऐसा करने के तरीके:

@Override 
    protected void updateItem(Double item, boolean empty) { 
     super.updateItem(item, empty); 
     if (empty || item == null) { 
      setText(null); 
      setTextFill(null); 
      return; 
     } 
     setText(String.valueOf(item)); 
     setTextFill(fill); 
    } 

यहाँ अपने प्रोग्राम है जो और अधिक आसानी से इस मुद्दे को दोहराता है और ठीक दर्शाता है करने के लिए एक छोटे से अद्यतन है। यदि आप setText (null) और setTextFill (null) लाइनों पर टिप्पणी करते हैं, तो कुछ बटन दबाएं, फिर बटन दबाएं, आप देखेंगे कि TableView वास्तव में अंतर्निहित सूची की स्थिति को प्रतिबिंबित नहीं करता है। लेकिन वहां नल सेटर्स के साथ, सब कुछ ठीक से सिंक में है। यह एक गोचा है ...

import javafx.application.Application; 
import javafx.beans.property.*; 
import javafx.scene.Scene; 
import javafx.scene.control.Button; 
import javafx.scene.control.*; 
import javafx.scene.control.cell.PropertyValueFactory; 
import javafx.scene.layout.AnchorPane; 
import javafx.scene.layout.VBox; 
import javafx.scene.paint.Color; 
import javafx.stage.Stage; 
import javafx.util.Callback; 

public class TestFX extends Application { 

    @Override 
    public void start(final Stage stage) throws Exception { 
     MyTable table = new MyTable(); 

     System.getProperties().list(System.out); 

     Scene scene = new Scene(table); 

     stage.setScene(scene); 
     stage.show(); 
    } 

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

    static class MyTable extends AnchorPane { 

     private static final Callback NUMBER_CELL_FACTORY = (p) -> new NumberTableCell<>(); 

     private final Button addRow = new Button("+"); 
     private final Button removeRow = new Button("-"); 
     private final TableView<Item> table = new TableView<>(); 

     MyTable() { 
      super(); 
      initTableView(); 
      addRow.setOnMouseClicked((e) -> addItem()); 
      removeRow.setOnMouseClicked((e) -> removeItem()); 
      VBox vbox = new VBox(5); 
      vbox.getChildren().addAll(addRow, removeRow, table); 
      getChildren().add(vbox); 
     } 

     public void addItem() { 
      table.getItems().addAll(new Item()); 
     } 

     public void removeItem() { 
      if (table.getItems().size() > 0) { 
       table.getItems().remove(0); 
      } 
     } 

     private void initTableView() { 
      TableColumn<Item, Double> value = new TableColumn<>("Value"); 
      value.setCellValueFactory(new PropertyValueFactory<>("value")); 
      value.setCellFactory(NUMBER_CELL_FACTORY); 

      table.getColumns().add(value); 
      table.setColumnResizePolicy(TableView.CONSTRAINED_RESIZE_POLICY); 
     } 
    } 

    public static class Item { 
     private final DoubleProperty value = new SimpleDoubleProperty(); 

     public DoubleProperty valueProperty() { 
      return value; 
     } 
    } 

    static class NumberTableCell<T> extends TableCell<T, Double> { 
     private final Color fill = Color.LIGHTGREY; 

     @Override 
     protected void updateItem(Double item, boolean empty) { 
      super.updateItem(item, empty); 
      if (empty || item == null) { 
       setText(null); 
       setTextFill(null); 
       return; 
      } 
      setText(String.valueOf(item)); 
      setTextFill(fill); 
     } 
    } 
} 
संबंधित मुद्दे