JavaFX:切换Locale时触发ChoiceBox转换器并排序显示文本
问题解决:Locale切换时更新ChoiceBox翻译并排序
触发转换器更新显示
JavaFX的ChoiceBox不会自动感知转换器依赖的资源变化,要刷新显示,最直接的方式是重新设置一次选项列表,或者如果使用ObservableList作为选项容器,可调用list.refresh()方法,强制ChoiceBox重新调用转换器的toString()方法生成新的翻译文本。
按翻译字符串排序
要按当前语言下的显示文本排序,需按以下步骤操作:
- 先保存当前选中的
SavingOrder,避免排序后选中状态丢失 - 基于当前Locale对应的翻译字符串,对枚举数组进行排序
- 将排序后的列表设置回ChoiceBox,再恢复之前的选中状态
修改后的完整代码
setChoiceBoxItems(settingsLangCB, supportedLocales); settingsLangCB.setConverter(new StringConverter<Locale>() { @Override public String toString(Locale locale) { String str = locale.getDisplayLanguage(locale); return str.substring(0, 1).toUpperCase() + str.substring(1); } @Override public Locale fromString(String string) { return null; } }); settingsLangCB.getSelectionModel().select(ioManager.getLoginAccount().getLocale()); settingsLangCB.setOnAction(event -> { Locale locale = settingsLangCB.getSelectionModel().getSelectedItem(); langResources.setResources(ResourceBundle.getBundle("/bundles/Lang", locale)); ioManager.getLoginAccount().setLocale(locale); // 处理SavingOrder ChoiceBox的翻译更新与排序 SavingOrder selectedOrder = settingsOrderCB.getSelectionModel().getSelectedItem(); // 按当前翻译字符串排序枚举值 SavingOrder[] sortedOrders = Arrays.stream(SavingOrder.class.getEnumConstants()) .sorted(Comparator.comparing(order -> langResources.getValue(order.i18nKey()))) .toArray(SavingOrder[]::new); // 重新设置选项,触发转换器刷新显示 setChoiceBoxItems(settingsOrderCB, sortedOrders); // 恢复之前选中的项 settingsOrderCB.getSelectionModel().select(selectedOrder); setMainTitle(langResources.getValue("settings")); }); setChoiceBoxItems(settingsOrderCB, SavingOrder.class.getEnumConstants()); settingsOrderCB.setConverter(new StringConverter<SavingOrder>() { @Override public String toString(SavingOrder savingOrder) { return langResources.getValue(savingOrder.i18nKey()); } @Override public SavingOrder fromString(String string) { return null; } }); settingsOrderCB.getSelectionModel().select(ioManager.getLoginAccount().getSavingOrder()); settingsOrderCB.setOnAction(event -> { SavingOrder savingOrder = settingsOrderCB.getSelectionModel().getSelectedItem(); ioManager.getLoginAccount().setSavingOrder(savingOrder); ioManager.sortAccountList(); });
补充说明
- 如果
setChoiceBoxItems方法内部使用ObservableList,可替换为调用list.refresh()刷新显示,但排序仍需重新生成有序列表。 - 排序时使用
Comparator.comparing直接基于翻译后的字符串比较,会自动遵循当前Locale的排序规则。
内容的提问来源于stack exchange,提问作者Achille004
相关产品推荐
相关产品推荐

