[英]How to change language at runtime in java swing
我嘗試在swing應用程序中運行時更改Locale。
但我無法弄清楚它應該如何運作,或者沒有總體規划?
我只能想到兩個選擇:
1.重新啟動應用程序,而不是最佳用戶體驗。
2.創建一個可以注冊/取消注冊組件的本地化管理器,在更改時它只是迭代所有組件並更改文本。
1和2都感覺很尷尬。
其他信息:
目前,方向不是目標。
該應用程序是混淆的。
例:
LocRes_en.properties:
text1 = English text
LocRes_ja.properties
text1 = Japanese text
ChangeLocale.java:
import java.awt.EventQueue; import java.awt.FlowLayout; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.util.Locale; import java.util.ResourceBundle; import javax.swing.JButton; import javax.swing.JFrame; import javax.swing.JLabel; public class ChangeLocale { private JFrame frame; public static void main(String[] args) { EventQueue.invokeLater(new Runnable() { public void run() { try { ChangeLocale window = new ChangeLocale(); window.frame.setVisible(true); } catch (Exception e) { e.printStackTrace(); } } }); } public ChangeLocale() { initialize(); } private void initialize() { frame = new JFrame(); frame.setBounds(100, 100, 450, 300); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); FlowLayout flowLayout = new FlowLayout(FlowLayout.CENTER, 5, 5); frame.getContentPane().setLayout(flowLayout); JButton btnChangeLoc = new JButton("Change Locale"); frame.getContentPane().add(btnChangeLoc); final JLabel lblLabel1 = new JLabel("New label"); frame.getContentPane().add(lblLabel1); Locale.setDefault(new Locale("en")); ResourceBundle r = ResourceBundle.getBundle("LocRes"); lblLabel1.setText(r.getString("text1")); btnChangeLoc.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { Locale.setDefault(new Locale("ja")); ResourceBundle r = ResourceBundle.getBundle("LocRes"); // Manually iterate through all components :( lblLabel1.setText(r.getString("text1")); // } }); } }
你可以嘗試LocaleChangeListener接口 -
我已經使用ResourceBundles和EventBus實現了這個功能 。
更改語言環境后,EventBus將觸發localeChangedEvent
。 所有具有本地化字符串的JFrame
窗口都必須訂閱此事件。 它們還必須實現一個changeLocale()
方法,該方法在收到事件時執行。
在此方法中,所有字符串都將更新為當前語言環境。
public void changeLocale(ResourceBundle rb) {
lblLabel1.setText(rb.getString("text1"));
lblLabel2.setText(rb.getString("text2"));
...
}
我曾經做過類似的事情。 雖然我的任務更簡單:這是一個系統托盤應用程序,所以我只需要更改菜單項文本。
但在你的情況下,我認為這是可行的。 首先,避免GUI層中的硬編碼字符串。 創建更改區域設置的類,然后遍歷所有可見框架並轉到所有面板和組件並更改寫在其上的文本。 我唯一能想到的問題是在畫布上繪制的文字。
使用支持的語言定義GUI
和組合框。 添加ItemListener
以便在更改組合框時更新文本。
LanguageGUIClient.java:
import javax.swing.*;
public class LanguageGUIClient
{
public static void main(String[] arguments) throws Exception
{
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
SwingUtilities.invokeLater(() ->
{
LanguageGUI languageGUI = new LanguageGUI();
languageGUI.setVisible(true);
});
}
}
LanguageGUI.java:
import javax.swing.*;
import java.util.Locale;
import java.util.ResourceBundle;
public class LanguageGUI extends JFrame
{
public static ResourceBundle resourceBundle;
private JPanel rootPanel;
private JComboBox<Locale> languageComboBox;
private JLabel languageLabel;
public LanguageGUI()
{
configureFrameProperties();
}
private void configureFrameProperties()
{
add(rootPanel);
setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
languageComboBox.addItem(Locale.US);
languageComboBox.addItem(Locale.GERMANY);
languageComboBox.addItem(Locale.FRANCE);
setTexts();
languageComboBox.addItemListener(itemEvent -> setTexts());
setSize(300, 100);
}
private void setTexts()
{
Locale locale = languageComboBox.getItemAt(languageComboBox.getSelectedIndex());
resourceBundle = ResourceBundle.getBundle("Bundle", locale);
setTitle(resourceBundle.getString("application.title"));
languageLabel.setText(resourceBundle.getString("language") + ":");
languageComboBox.setToolTipText(resourceBundle.getString("language.tooltip"));
}
}
請注意,我正在使用IntelliJ's form designer
因此.form
文件內容也是必需的。
LanguageGUI.form:
<?xml version="1.0" encoding="UTF-8"?>
<form xmlns="http://www.intellij.com/uidesigner/form/" version="1" bind-to-class="LanguageGUI">
<grid id="27dc6" binding="rootPanel" layout-manager="GridLayoutManager" row-count="2" column-count="2" same-size-horizontally="false" same-size-vertically="false" hgap="-1" vgap="-1">
<margin top="0" left="0" bottom="0" right="0"/>
<constraints>
<xy x="20" y="20" width="500" height="400"/>
</constraints>
<properties/>
<border type="none"/>
<children>
<component id="eb651" class="javax.swing.JComboBox" binding="languageComboBox">
<constraints>
<grid row="0" column="1" row-span="1" col-span="1" vsize-policy="0" hsize-policy="2" anchor="8" fill="1" indent="0" use-parent-layout="false"/>
</constraints>
<properties>
<toolTipText value=""/>
</properties>
</component>
<vspacer id="977c1">
<constraints>
<grid row="1" column="1" row-span="1" col-span="1" vsize-policy="6" hsize-policy="1" anchor="0" fill="2" indent="0" use-parent-layout="false"/>
</constraints>
</vspacer>
<component id="e59f" class="javax.swing.JLabel" binding="languageLabel">
<constraints>
<grid row="0" column="0" row-span="1" col-span="1" vsize-policy="0" hsize-policy="0" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
</constraints>
<properties>
<text value=""/>
</properties>
</component>
</children>
</grid>
</form>
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.