2014-02-11 93 views
3

假設我有一個地圖收藏:JavaFX的:將行添加到TableView中有一個HashMap結合

ObserableHashMap<K,V> map = FXCollections.observableHashMap(); 

我把1個記錄到這個地圖FXML控制器初始化過程,然後把它包裝成ObservableList

ObservableList<ObserableHashMap.Entry<K,V>> list = FXCollections.observableArrayList(map.entrySet()); 

然後setitemstableView.setItems(list);

一切都很好,當我運行這個應用程序的JavaFX和1個記錄被顯示。

問題是:

當我更多的記錄後添加到我的地圖,我的TableView不會刷新這些記錄。

如何將動態地圖集合綁定到我的TableView

感謝

+0

順便說一句,一旦我將ObserableHashMap地圖更改爲ObserableArrayList – user2196346

+0

請儘快安排,請添加一些代碼來證明問題。只有3行代碼很難看出你的問題。 –

回答

1

您可以將地圖直接綁定到一個TableView中,從JavaFX的文檔考慮這個例子:

import java.util.HashMap; 
import java.util.Map; 
import javafx.application.Application; 
import javafx.collections.FXCollections; 
import javafx.collections.ObservableList; 
import javafx.geometry.Insets; 
import javafx.scene.Group; 
import javafx.scene.Scene; 
import javafx.scene.control.Label; 
import javafx.scene.control.TableCell; 
import javafx.scene.control.TableColumn; 
import javafx.scene.control.TableView; 
import javafx.scene.control.cell.MapValueFactory; 
import javafx.scene.control.cell.TextFieldTableCell; 
import javafx.scene.layout.VBox; 
import javafx.scene.text.Font; 
import javafx.stage.Stage; 
import javafx.util.Callback; 
import javafx.util.StringConverter; 

public class TableViewSample extends Application { 

    public static final String Column1MapKey = "A"; 
    public static final String Column2MapKey = "B"; 

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

    @Override 
    public void start(Stage stage) { 
     Scene scene = new Scene(new Group()); 
     stage.setTitle("Table View Sample"); 
     stage.setWidth(300); 
     stage.setHeight(500); 

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

     TableColumn<Map, String> firstDataColumn = new TableColumn<>("Class A"); 
     TableColumn<Map, String> secondDataColumn = new TableColumn<>("Class B"); 

     firstDataColumn.setCellValueFactory(new MapValueFactory(Column1MapKey)); 
     firstDataColumn.setMinWidth(130); 
     secondDataColumn.setCellValueFactory(new MapValueFactory(Column2MapKey)); 
     secondDataColumn.setMinWidth(130); 

     TableView table_view = new TableView<>(generateDataInMap()); 

     table_view.setEditable(true); 
     table_view.getSelectionModel().setCellSelectionEnabled(true); 
     table_view.getColumns().setAll(firstDataColumn, secondDataColumn); 
     Callback<TableColumn<Map, String>, TableCell<Map, String>> 
      cellFactoryForMap = new Callback<TableColumn<Map, String>, 
       TableCell<Map, String>>() { 
        @Override 
        public TableCell call(TableColumn p) { 
         return new TextFieldTableCell(new StringConverter() { 
          @Override 
          public String toString(Object t) { 
           return t.toString(); 
          } 
          @Override 
          public Object fromString(String string) { 
           return string; 
          }          
         }); 
        } 
     }; 
     firstDataColumn.setCellFactory(cellFactoryForMap); 
     secondDataColumn.setCellFactory(cellFactoryForMap); 

     final VBox vbox = new VBox(); 

     vbox.setSpacing(5); 
     vbox.setPadding(new Insets(10, 0, 0, 10)); 
     vbox.getChildren().addAll(label, table_view); 

     ((Group) scene.getRoot()).getChildren().addAll(vbox); 

     stage.setScene(scene); 

     stage.show(); 
    } 

    private ObservableList<Map> generateDataInMap() { 
     int max = 10; 
     ObservableList<Map> allData = FXCollections.observableArrayList(); 
     for (int i = 1; i < max; i++) { 
      Map<String, String> dataRow = new HashMap<>(); 

      String value1 = "A" + i; 
      String value2 = "B" + i; 

      dataRow.put(Column1MapKey, value1); 
      dataRow.put(Column2MapKey, value2); 

      allData.add(dataRow); 
     } 
     return allData; 
    } 
} 

的更多信息,可以發現here

+0

是的,我可以直接綁定地圖,但是我在初始化後添加的數據項不會顯示出來,如果我切換到ObservableList,它將顯示相同的代碼。 – user2196346

+0

你可以請張貼一些代碼,爲更好的清晰度你如何使用地圖 – ItachiUchiha

1

從ItachiUchiha答案使用列作爲鍵和行作爲單獨的地圖。如果您希望將一行地圖的行作爲鍵 - >值,則必須向地圖添加偵聽器,以便在添加或刪除時更改列表。我在這裏做了類似的事情。 https://stackoverflow.com/a/21339428/2855515

+0

哦,有我的代碼(開始在Lobby.java,對不起,不知道如何張貼在這裏):http://stackoverflow.com/questions/ 16941980 /填充-的tableview與 - observablemap-JavaFX的?LQ = 1 – user2196346

4

如果使用ObservableMaps的ObservableList爲您的TableView的數據結構

ObservableList<ObservableMap> rowMaps = FXCollections.observableArrayList(); 
tableView.setItems(rowMaps); 

,並實現自己的ObservableMapValueFactory

import javafx.beans.property.ObjectProperty; 
import javafx.beans.property.SimpleObjectProperty; 
import javafx.beans.value.ObservableValue; 
import javafx.collections.MapChangeListener; 
import javafx.collections.ObservableMap; 
import javafx.scene.control.TableColumn; 
import javafx.scene.control.TableColumn.CellDataFeatures; 
import javafx.util.Callback; 

public class ObservableMapValueFactory<V> implements 
     Callback<TableColumn.CellDataFeatures<ObservableMap, V>, ObservableValue<V>> { 

    private final Object key; 

    public ObservableMapValueFactory(Object key) { 
     this.key = key; 
    } 

    @Override 
    public ObservableValue<V> call(CellDataFeatures<ObservableMap, V> features) { 
     final ObservableMap map = features.getValue(); 
     final ObjectProperty<V> property = new SimpleObjectProperty<V>((V) map.get(key)); 
     map.addListener(new MapChangeListener<Object, V>() { 
      public void onChanged(Change<?, ? extends V> change) { 
       if (key.equals(change.getKey())) { 
        property.set((V) map.get(key)); 
       } 
      } 
     }); 
     return property; 
    } 
} 

,然後將其設置爲單元格值廠家爲列(S )

column.setCellValueFactory(new ObservableMapValueFactory<String>(columnId)); 

全部變化到你的數據都反映在TableView中,即使更改隻影響ObservableMaps。

相關問題