我正在使用JavaFX为GUI创建聊天应用程序 . 我在ListView中显示聊天内容,但我有一个大问题 - 它非常慢 . 当我向列表中添加新项目时,尤其是当我向上/向下滚动列表时 . 我想也许这与列表刷新itsellf每次添加新项目(列表中的每个单元格!)以及每次向上/向下滚动时都刷新的事实有关 . 有人知道我该怎么做才能解决这个问题? TNX
我重写ListCell的updateItem:
chatListView.setCellFactory(new Callback,ListCell>(){@ Overver public ListCell call(ListView p){ListCell cell = new ListCell(){@ Override protected void updateItem(UserInfo item,boolean bln){super.updateItem(item,bln) );
if (item != null) {
BorderPane borderPane = new BorderPane();
ImageView profileImage = new ImageView(new Image(item.getImageURL()));
profileImage.setFitHeight(32);
profileImage.setFitWidth(32);
Rectangle clip = new Rectangle(
profileImage.getFitWidth(), profileImage.getFitHeight()
);
clip.setArcWidth(30);
clip.setArcHeight(30);
profileImage.setClip(clip);
SnapshotParameters parameters = new SnapshotParameters();
parameters.setFill(Color.TRANSPARENT);
WritableImage image = profileImage.snapshot(parameters, null);
profileImage.setClip(null);
profileImage.setImage(image);
ImageView arrowImage = new ImageView(new Image("arrow1.png"));
ImageView arrowImage2 = new ImageView(new Image("arrow1.png"));
Label nameLabel = new Label(item.getUserName());
nameLabel.setStyle(" -fx-text-alignment: center; -fx-padding: 2;");
HBox hbox = null;
Label textLabel = new Label();
String messageText = splitTolines(item.getMessage());
textLabel.setText(messageText);
textLabel.setStyle("-fx-background-color: #a1f2cd; "
+ "-fx-padding: 10;\n"
+ "-fx-spacing: 5;");
hbox = new HBox(arrowImage, textLabel);
VBox vbox = new VBox(profileImage, nameLabel);
BorderPane.setMargin(vbox, new Insets(0, 10, 10, 10));
BorderPane.setMargin(hbox, new Insets(10, 0, 0, 0));
//Time
Date dNow = new Date();
SimpleDateFormat ft = new SimpleDateFormat("hh:mm a");
Label timeLabel = new Label(ft.format(dNow));
timeLabel.setStyle("-fx-font: 8px Tahoma; -fx-width: 100%");
HBox hbox2 = new HBox(arrowImage2, timeLabel);
arrowImage2.setVisible(false);
VBox vbox2 = new VBox(hbox, hbox2);
borderPane.setCenter(vbox2);
borderPane.setLeft(vbox);
setGraphic(borderPane);
}
}
};
return cell;
}
});
3 回答
1.) Never ever 在
updateItem()
中添加(大)GUI元素,而不检查它是否已经存在 .1.1)当你以任何其他方式滚动,调整大小或改变gui时,每次为 EVERY SINGLE ROW 调用
updateItem()
.1.2)如果你没有项目或
updateItem(item, empty)
的第二个布尔值为false,你应该总是 reset the graphic to null ,因为第二个布尔值是 EMPTY 标志 .2.)我建议您使用VBox而不是ListView . ;-)
快乐的编码,
Kalasch
每次更新视图时,都不得构建组件的新实例 .
最初对它们进行一次初始化,然后重用并更改其属性 .
我也注意到了 . 即使对于仅包含5-10个项目的列表(具有缩放图像和文本),它也太慢 . 由于我不需要选择功能,我还重写了使用VBox的代码,而且速度很快就消失了!
为了模拟setItems,我有一个辅助函数,你可以找到它:
它可以像以下一样使用:
从可观察列表中自动更新列表(VBox的子项) .
PS:其他功能如分组在这里=> ObservableListHelper