Search code examples
hashmapjavafx-8observablecollection

Using JavaFX, displaying contents of a hashmap in a tableview


I have a TableView within which I want to display a list of features and properties of equipment which is stored in a HashMap<Integer, CustomClass> that will update when new items are added to the HashMap.
I have tried different ways to get the data to display but been unsuccessful and looked over examples in other questions but it doesn't seem to work. Maybe I'm confused because my javaFX layout is using a FXML and controller class approach that doesn't match most examples.
Can anyone help point out what I'm doing wrong?

Here's the code in the controller:

public class MainController implements Initializable {

    @FXML 
    private ToggleButton activateBtn;
    @FXML
    private Label dispTime;
    @FXML
    private Button timeControl;
    @FXML
    private ChoiceBox paceNum;
    @FXML
    private TableView<Map> trainTable;
    @FXML
    private TableColumn trainIdCol;
    @FXML
    private TableColumn speedCol;
    @FXML
    private TableColumn authCol;
    @FXML
    private TableColumn trainTimeCol;
    @FXML
    private TableColumn driverCol;
    @FXML
    private TableColumn driverTimeCol;
    @FXML
    private TableColumn lineCol;
    @FXML
    private TableColumn directionCol;
    @FXML
    private TableColumn locColX;
    @FXML
    private TableColumn locColY;
    @FXML
    private TableColumn destCol;
    @FXML
    private TableColumn timeToCol;
    @FXML
    private TextArea ta;
    @FXML
    private MenuItem closeButton;


    /*
     * get all the trains to display
     */
    static final ObservableList<HashMap<Integer, MboTrain>> trainList = FXCollections.observableArrayList(MboTrain.trainList);



    @Override
    public void initialize(URL url, ResourceBundle rb) {
        reportData(">System initializing...");


        /*
         * Identify which train values to list in the train table
         */
        trainIdCol.setCellValueFactory(new MapValueFactory("trainId"));
        speedCol.setCellValueFactory(new MapValueFactory("speed"));
        authCol.setCellValueFactory(new MapValueFactory("authority"));
        trainTimeCol.setCellValueFactory(new MapValueFactory("trainTime"));
        driverCol.setCellValueFactory(new MapValueFactory("driverId"));
        driverTimeCol.setCellValueFactory(new MapValueFactory("driverTime"));
        lineCol.setCellValueFactory(new MapValueFactory("line"));
        directionCol.setCellValueFactory(new MapValueFactory("direction"));
        locColX.setCellValueFactory(new MapValueFactory("currentLoc"));
        locColY.setCellValueFactory(new MapValueFactory("currentLoc"));
        destCol.setCellValueFactory(new MapValueFactory("nextLoc"));
        timeToCol.setCellValueFactory(new MapValueFactory("timeToNext"));

        /*
         * mark the columns as Map read values
         */
        Callback<TableColumn<Map, String>, TableCell<Map, String>>
                cellFactoryForMap = null;
        trainIdCol.setCellFactory(cellFactoryForMap);
        speedCol.setCellFactory(cellFactoryForMap);
        authCol.setCellFactory(cellFactoryForMap);
        trainTimeCol.setCellFactory(cellFactoryForMap);
        driverCol.setCellFactory(cellFactoryForMap);
        driverTimeCol.setCellFactory(cellFactoryForMap);
        lineCol.setCellFactory(cellFactoryForMap);
        directionCol.setCellFactory(cellFactoryForMap);
        locColX.setCellFactory(cellFactoryForMap);
        locColY.setCellFactory(cellFactoryForMap);
        destCol.setCellFactory(cellFactoryForMap);
        timeToCol.setCellFactory(cellFactoryForMap);
        /*
         * call the update method to have the MBO pull a list of active trains into the table
         */
        try {
            MboTrain.updateTrainList();
        } catch (IOException e) {
            e.printStackTrace();
        }
        /*
         * establish table properties and get the data for the columns
         */
        trainTable.setEditable(false);
        trainTable.getSelectionModel().setCellSelectionEnabled(false);
        trainTable.getColumns().setAll(trainIdCol, speedCol, authCol, trainTimeCol, driverCol, driverTimeCol,
                lineCol, directionCol, locColX, locColY, destCol, timeToCol);

        /*
         * run the callback method to have the columns callback to a Map for data
         */
        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;
                    }
                });
            }
        };
    }

And the custom class object:

public class MboTrain {

    /*
     * list of trains created in the system
     */
    private static ArrayList<Integer> trainListPull;
    public static HashMap<Integer, MboTrain> trainList;

    private Integer trainId;
    private double speed;
    private double authority;
    private long trainStartTime;
    private long trainTime;
    private int driverId;
    private long driverTime;
    private LineId line;
    private Boolean direction;
    private String directionString;
    private double currentLocX;
    private double currentLocY;
    private Block nextBlock;
    private Station nextStation;
    private Block nextStationBlock;
    private long timeToNext;


    private Block[] track;
    private Route route;
    private Block destinationBlock;
    private Block currentBlock;


    /*
     * generates a default train object and places it in the map
     */
    public MboTrain(LineId m_line) throws IOException {
        int pId = createTrain("MboCreatedTrain");
        placeTrainOnLine(pId, m_line);
        this.line = m_line;
        this.trainId = pId;
        this.speed = 0;
        this.authority = 0;
        this.trainStartTime = MboClock.updateTime();
        this.trainTime = 0;
        this.driverId = 0;
        this.driverTime = 0;
        this.line = m_line;
        this.direction = true;
        this.directionString = "outbound";
        this.currentLocX = 0;
        this.currentBlock = MboTrack.getYard(m_line);
        this.nextBlock = getNextBlock();
        this.nextStationBlock = this.nextBlock;
        this.setNextStation();
        this.timeToNext = 0;
        this.route = null;
        if (trainList == null)
        {
            trainList = new HashMap<>();
        }
        trainList.put(pId,this);
    }

    public static boolean createMboTrain(LineId m_line) throws IOException
    {
        MboTrain m_train = new MboTrain(m_line);
        if (m_train == null)
        {
            return false;
        }
        else
        {
            return true;
        }
    }

    /*
     * update the list of available trains from train model handler
     */
    public static void updateTrainList() throws IOException {
        trainListPull = getTrainList();
        LineId line;
        MboTrain m_train;
        trainList = new HashMap<>();
        for (Integer tid : trainListPull) {
            System.out.println("well, we're checking the trainlist map for "+tid);
            if (trainList.containsKey(tid))
            {
                // do nothing since train already in map
                System.out.println("doing nothing - already in map");
            }
            else
            {
                if (trainLineMap.containsKey(tid)) {
                    System.out.println("train is on a line - creating train on a line and adding to map");
                    line = trainLineMap.get(tid);
                    m_train = new MboTrain(line);
                    //m_train.getCurrentLoc();
                    trainList.put(tid, m_train);
                    System.out.println("success - we've added train "+tid+" on line "+line.toString()+" to the map");
                } else {
                    System.out.println("train isn't on a line - so creating train with null lineId and adding to map");
                    m_train = new MboTrain(null);
                    trainList.put(tid, m_train);
                    System.out.println("success - we've added train "+tid+" to the map with line=null");
                }
            }
        }
    }

Any help is appreciated!!


Solution

  • I realize I'm just coming at this all wrong. So I'm going to follow James_D's advice and look at using just an ObservableList representation of the map and display that list. I'm marking this closed so I don't waste anyone's time on this.
    Thanks