JavaFX:ObservableLists,ClassCastException:A不能转换为B

时间:2016-04-01 21:04:34

标签: java listview javafx

我正在尝试在JavaFX中创建GUI。我有一个ListView我想用来显示一些数据。我想要使​​用两种类型的可能数据集,我们称之为汽车和自行车。当我按下相应的按钮时,我想加载我需要的数据。到目前为止,我的控制器类看起来像这样:

import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.fxml.FXML;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.util.Callback;


import java.util.List;

public class FXMLController {
    @FXML
    ListView lv_list;
    @FXML
    Button button_cars;
    @FXML
    Button button_bikes;


    List<Cars> cList;
    List<Bikes> bList;
    Server serv;

    private ObservableList observableList = FXCollections.observableArrayList();

    public void initScene szene) {
        /* initializes serv so it properly yields data */
    }


    public void listAllCars() {
        cList = serv.getAllCars();
        updateCarList();
    }

    private void updateCarList() {
        observableList.setAll(cList);
        lv_list.setItems(observableList);
        lv_list.setCellFactory(new Callback<ListView<Cars>, ListCell<Cars>>() {
            @Override
            public ListCell<Cars> call(ListView<Cars> listView) {
                return new ListViewElemCars(); // creates stuff to populate the list
            }
        });
    }

    public void listAllBikes() {
        bList = serv.getAllBikes();
        updateBikeList();
    }

    private void updateBikeList() {
        observableList.setAll(bList);
        lv_list.setItems(observableList);
        lv_list.setCellFactory(new Callback<ListView<Bikes>, ListCell<Bikes>>() {
            @Override
            public ListCell<Bikes> call (ListView<Bikes> listView) {
                return new ListViewElemBikes(); //same as with cars
            }
        });
    }
}

只要按下其中一个按钮,就会发生列表方法。这些方法本身效果很好 - 如果按下汽车按钮,所有汽车都会按照预期的方式显示出来。自行车也是如此。但是,当我尝试一个接一个地按下时,我收到以下错误:

Exception in thread "JavaFX Application Thread" java.lang.ClassCastException: Cars cannot be cast to Bikes

我想这是由于updateCarList / updateBikeList方法中未经检查的调用,但我真的不知所措。我想以某种方式能够用一个ListView做这个东西,但我真的不明白这里有什么问题。我在这里缺少什么?

1 个答案:

答案 0 :(得分:1)

您在cellFactory返回的单元格中使用具体类型。当新项目类型被添加到不打算显示新类型项目的单元格时,ListView将重复使用导致ClassCastException的单元格。

即使以下方法似乎也不起作用:

  1. 清除items列表
  2. 替换cellFactory
  3. 致电refresh()
  4. 添加新的items
  5. 这意味着您必须使用可以处理所有项类型的单元格,或者替换整个ListView