!38 #I7W8LM 国际化和本地化使用i18n
Merge pull request !38 from songdragon/refactor-I7W8LM
This commit is contained in:
commit
2eb71bece8
7
.idea/encodings.xml
generated
Normal file
7
.idea/encodings.xml
generated
Normal file
@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="Encoding" defaultCharsetForPropertiesFiles="UTF-8">
|
||||
<file url="file://$PROJECT_DIR$/src/main/java" charset="UTF-8" />
|
||||
<file url="file://$PROJECT_DIR$/src/main/resources" charset="UTF-8" />
|
||||
</component>
|
||||
</project>
|
||||
@ -9,10 +9,12 @@ import javafx.scene.image.Image;
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.stage.Stage;
|
||||
import org.jcnc.jnotepad.app.config.LocalizationConfig;
|
||||
import org.jcnc.jnotepad.app.i18n.UIResourceBundle;
|
||||
import org.jcnc.jnotepad.app.init.LoadJnotepadConfig;
|
||||
import org.jcnc.jnotepad.app.init.LoadLanguageConfig;
|
||||
import org.jcnc.jnotepad.app.init.LoadShortcutKeyConfig;
|
||||
import org.jcnc.jnotepad.constants.AppConstants;
|
||||
import org.jcnc.jnotepad.constants.TextConstants;
|
||||
import org.jcnc.jnotepad.controller.manager.Controller;
|
||||
import org.jcnc.jnotepad.manager.ThreadPoolManager;
|
||||
import org.jcnc.jnotepad.ui.LineNumberTextArea;
|
||||
@ -82,7 +84,7 @@ public class LunchApp extends Application {
|
||||
viewManager.initScreen(scene);
|
||||
// 加载配置文件
|
||||
View.getInstance().initJnotepadConfigs(LOAD_JNOTEPAD_CONFIGS);
|
||||
primaryStage.setTitle(localizationConfig.getTitle());
|
||||
UIResourceBundle.bindStringProperty(primaryStage.titleProperty(), TextConstants.TITLE);
|
||||
primaryStage.setWidth(width);
|
||||
primaryStage.setHeight(length);
|
||||
primaryStage.setScene(scene);
|
||||
|
||||
@ -31,4 +31,5 @@ public class GlobalConfig {
|
||||
public static GlobalConfig getConfig() {
|
||||
return APP_GLOBAL_CONFIG;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -1,12 +1,13 @@
|
||||
package org.jcnc.jnotepad.app.config;
|
||||
|
||||
import org.jcnc.jnotepad.LunchApp;
|
||||
import org.jcnc.jnotepad.app.i18n.UIResourceBundle;
|
||||
import org.jcnc.jnotepad.tool.LogUtil;
|
||||
import org.slf4j.Logger;
|
||||
|
||||
import java.io.*;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.Properties;
|
||||
import java.util.*;
|
||||
|
||||
import static org.jcnc.jnotepad.constants.AppConstants.APP_NAME;
|
||||
import static org.jcnc.jnotepad.constants.TextConstants.*;
|
||||
@ -14,300 +15,58 @@ import static org.jcnc.jnotepad.constants.TextConstants.*;
|
||||
/**
|
||||
* 本地化配置文件<br>
|
||||
* 注意:该配置文件必须先于快捷键配置文件加载
|
||||
* @see LunchApp
|
||||
*
|
||||
* @author gewuyou
|
||||
* @see LunchApp
|
||||
*/
|
||||
public class LocalizationConfig {
|
||||
Logger logger = LogUtil.getLogger(this.getClass());
|
||||
private static final LocalizationConfig LOCALIZATION_CONFIG = new LocalizationConfig();
|
||||
private final Properties properties = new Properties();
|
||||
|
||||
/**
|
||||
* 本地化语言包名,默认英文
|
||||
*/
|
||||
private String languagePackName = EN_LANGUAGE_PACK_NAME;
|
||||
private String language;
|
||||
|
||||
private static final Map<String, Locale> SUPPORT_LOCALES;
|
||||
private static final Map<Locale, String> SUPPORT_LANGUAGES;
|
||||
|
||||
static {
|
||||
Locale.setDefault(Locale.ENGLISH);
|
||||
SUPPORT_LOCALES = new LinkedHashMap<>();
|
||||
SUPPORT_LOCALES.put(CHINESE, Locale.CHINESE);
|
||||
SUPPORT_LOCALES.put(ENGLISH, Locale.ENGLISH);
|
||||
|
||||
SUPPORT_LANGUAGES = new HashMap<>();
|
||||
SUPPORT_LANGUAGES.put(Locale.CHINESE, CHINESE);
|
||||
SUPPORT_LANGUAGES.put(Locale.ENGLISH, ENGLISH);
|
||||
}
|
||||
|
||||
public static final Locale getCurrentLocal() {
|
||||
return Locale.getDefault();
|
||||
}
|
||||
|
||||
public static final void setCurrentLocal(Locale locale) {
|
||||
Locale.setDefault(locale);
|
||||
UIResourceBundle.getInstance().resetLocal();
|
||||
LOCALIZATION_CONFIG.setLanguage(SUPPORT_LANGUAGES.get(locale));
|
||||
}
|
||||
|
||||
public static final void setCurrentLocal(String language) {
|
||||
Locale locale = SUPPORT_LOCALES.get(language);
|
||||
if (locale != null) {
|
||||
setCurrentLocal(locale);
|
||||
}
|
||||
}
|
||||
|
||||
private LocalizationConfig() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* 初始化本地化语言包
|
||||
*
|
||||
* @since 2023/8/25 18:18
|
||||
*/
|
||||
public void initLocalizationConfig() {
|
||||
// 设置语言包
|
||||
try (InputStream inputStream = new FileInputStream(languagePackName)) {
|
||||
// 使用 UTF-8 编码
|
||||
InputStreamReader reader = new InputStreamReader(inputStream, StandardCharsets.UTF_8);
|
||||
properties.load(reader);
|
||||
} catch (IOException e) {
|
||||
logger.info("未检测到本地化语言包!");
|
||||
// 如果读取出错,则调用初始化方法
|
||||
initializePropertiesFile();
|
||||
}
|
||||
logger.info("初始化本地化语言包成功!");
|
||||
title = properties.getProperty(TITLE, APP_NAME);
|
||||
sava = properties.getProperty(SAVE);
|
||||
file = properties.getProperty(FILE);
|
||||
newly = properties.getProperty(NEW);
|
||||
open = properties.getProperty(OPEN);
|
||||
savaAs = properties.getProperty(SAVE_AS);
|
||||
set = properties.getProperty(SET);
|
||||
wordWrap = properties.getProperty(WORD_WRAP);
|
||||
plugin = properties.getProperty(PLUGIN);
|
||||
addPlugin = properties.getProperty(ADD_PLUGIN);
|
||||
statistics = properties.getProperty(STATISTICS);
|
||||
openConfigurationFile = properties.getProperty(OPEN_CONFIGURATION_FILE);
|
||||
top = properties.getProperty(TOP);
|
||||
language = properties.getProperty(LANGUAGE);
|
||||
chinese = properties.getProperty(UPPER_CHINESE);
|
||||
english = properties.getProperty(UPPER_ENGLISH);
|
||||
textWrap = properties.getProperty(TEXT_WRAP, "true");
|
||||
newFile = properties.getProperty(NEW_FILE);
|
||||
unknown = properties.getProperty(UNKNOWN);
|
||||
row = properties.getProperty(ROW);
|
||||
column = properties.getProperty(COLUMN);
|
||||
wordCount = properties.getProperty(WORD_COUNT);
|
||||
encode = properties.getProperty(ENCODE);
|
||||
}
|
||||
|
||||
/**
|
||||
* 初始化属性配置文件。
|
||||
* 如果属性文件不存在,将创建一个新的属性文件并设置默认属性。
|
||||
*/
|
||||
public void initializePropertiesFile() {
|
||||
switch (languagePackName) {
|
||||
case CH_LANGUAGE_PACK_NAME -> {
|
||||
setChineseLanguagePack();
|
||||
createLanguagePacks(languagePackName, properties);
|
||||
}
|
||||
case EN_LANGUAGE_PACK_NAME -> {
|
||||
setEnglishLanguagePack();
|
||||
createLanguagePacks(languagePackName, properties);
|
||||
}
|
||||
default -> logger.error("语言包加载错误!");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void createLanguagePacks(String languagePackName, Properties languagePack) {
|
||||
try (OutputStream outputStream = new FileOutputStream(languagePackName)) {
|
||||
// 使用 UTF-8 编码
|
||||
OutputStreamWriter writer = new OutputStreamWriter(outputStream, StandardCharsets.UTF_8);
|
||||
languagePack.store(writer, languagePackName);
|
||||
} catch (IOException ignored) {
|
||||
logger.info("未检测到语言包!");
|
||||
}
|
||||
}
|
||||
|
||||
private void setChineseLanguagePack() {
|
||||
properties.clear();
|
||||
// 设置默认属性
|
||||
properties.setProperty(TITLE, APP_NAME);
|
||||
properties.setProperty(NEW_FILE, "新建文件");
|
||||
properties.setProperty(SAVE, "保存");
|
||||
properties.setProperty(FILE, "文件");
|
||||
properties.setProperty(NEW, "新建");
|
||||
properties.setProperty(OPEN, "打开");
|
||||
properties.setProperty(SAVE_AS, "另存为");
|
||||
properties.setProperty(SET, "设置");
|
||||
properties.setProperty(WORD_WRAP, "自动换行");
|
||||
properties.setProperty(OPEN_CONFIGURATION_FILE, "打开配置文件");
|
||||
properties.setProperty(PLUGIN, "插件");
|
||||
properties.setProperty(ADD_PLUGIN, "增加插件");
|
||||
properties.setProperty(STATISTICS, "统计字数");
|
||||
properties.setProperty(ROW, "行数");
|
||||
properties.setProperty(COLUMN, "列数");
|
||||
properties.setProperty(WORD_COUNT, "字数");
|
||||
properties.setProperty(ENCODE, "编码");
|
||||
properties.setProperty(TOP, "窗口置顶");
|
||||
properties.setProperty(LANGUAGE, "语言");
|
||||
properties.setProperty(UPPER_CHINESE, "中文");
|
||||
properties.setProperty(UPPER_ENGLISH, "英文");
|
||||
}
|
||||
|
||||
private void setEnglishLanguagePack() {
|
||||
properties.clear();
|
||||
properties.setProperty(TITLE, APP_NAME);
|
||||
properties.setProperty(NEW_FILE, "New File");
|
||||
properties.setProperty(SAVE, "Save");
|
||||
properties.setProperty(FILE, "File");
|
||||
properties.setProperty(NEW, "New");
|
||||
properties.setProperty(OPEN, "Open");
|
||||
properties.setProperty(SAVE_AS, "Save As");
|
||||
properties.setProperty(SET, "Settings");
|
||||
properties.setProperty(WORD_WRAP, "Word Wrap");
|
||||
properties.setProperty(OPEN_CONFIGURATION_FILE, "Open Configuration File");
|
||||
properties.setProperty(PLUGIN, "Plugins");
|
||||
properties.setProperty(ADD_PLUGIN, "Add Plugin");
|
||||
properties.setProperty(STATISTICS, "Word Count");
|
||||
properties.setProperty(ROW, "Row");
|
||||
properties.setProperty(COLUMN, "Column");
|
||||
properties.setProperty(WORD_COUNT, "Word Count");
|
||||
properties.setProperty(ENCODE, "Encoding");
|
||||
properties.setProperty(TOP, "Window Top");
|
||||
properties.setProperty(LANGUAGE, "Language");
|
||||
properties.setProperty(UPPER_CHINESE, "Chinese");
|
||||
properties.setProperty(UPPER_ENGLISH, "English");
|
||||
}
|
||||
|
||||
private String textWrap;
|
||||
/// 应用程序文本
|
||||
|
||||
private String title;
|
||||
|
||||
///菜单栏文本
|
||||
|
||||
private String sava;
|
||||
|
||||
private String file;
|
||||
|
||||
private String newly;
|
||||
|
||||
private String open;
|
||||
|
||||
private String savaAs;
|
||||
|
||||
private String set;
|
||||
|
||||
private String wordWrap;
|
||||
|
||||
private String plugin;
|
||||
|
||||
private String addPlugin;
|
||||
|
||||
private String statistics;
|
||||
|
||||
private String openConfigurationFile;
|
||||
|
||||
private String top;
|
||||
|
||||
private String language;
|
||||
|
||||
private String chinese;
|
||||
|
||||
private String english;
|
||||
|
||||
/// NewFile 文本常量
|
||||
|
||||
private String newFile;
|
||||
/// EncodingDetector 文本常量
|
||||
/**
|
||||
* 未知
|
||||
*/
|
||||
private String unknown;
|
||||
|
||||
/// JNotepadStatusBox
|
||||
|
||||
private String row;
|
||||
|
||||
private String column;
|
||||
|
||||
private String wordCount;
|
||||
|
||||
private String encode;
|
||||
|
||||
public static LocalizationConfig getLocalizationConfig() {
|
||||
return LOCALIZATION_CONFIG;
|
||||
}
|
||||
|
||||
public void setLanguagePackName(String languagePackName) {
|
||||
this.languagePackName = languagePackName;
|
||||
}
|
||||
|
||||
public String getTitle() {
|
||||
return title;
|
||||
}
|
||||
|
||||
public String getSava() {
|
||||
return sava;
|
||||
}
|
||||
|
||||
public String getFile() {
|
||||
return file;
|
||||
}
|
||||
|
||||
public String getNewly() {
|
||||
return newly;
|
||||
}
|
||||
|
||||
public String getOpen() {
|
||||
return open;
|
||||
}
|
||||
|
||||
public String getSavaAs() {
|
||||
return savaAs;
|
||||
}
|
||||
|
||||
public String getSet() {
|
||||
return set;
|
||||
}
|
||||
|
||||
public String getWordWrap() {
|
||||
return wordWrap;
|
||||
}
|
||||
|
||||
public String getPlugin() {
|
||||
return plugin;
|
||||
}
|
||||
|
||||
public String getAddPlugin() {
|
||||
return addPlugin;
|
||||
}
|
||||
|
||||
public String getStatistics() {
|
||||
return statistics;
|
||||
}
|
||||
|
||||
public String getOpenConfigurationFile() {
|
||||
return openConfigurationFile;
|
||||
}
|
||||
|
||||
public String getTop() {
|
||||
return top;
|
||||
}
|
||||
|
||||
public String getLanguage() {
|
||||
return language;
|
||||
}
|
||||
|
||||
public String getChinese() {
|
||||
return chinese;
|
||||
}
|
||||
|
||||
public String getEnglish() {
|
||||
return english;
|
||||
}
|
||||
|
||||
public String getNewFile() {
|
||||
return newFile;
|
||||
}
|
||||
|
||||
public String getUnknown() {
|
||||
return unknown;
|
||||
}
|
||||
|
||||
public String getRow() {
|
||||
return row;
|
||||
}
|
||||
|
||||
public String getColumn() {
|
||||
return column;
|
||||
}
|
||||
|
||||
public String getWordCount() {
|
||||
return wordCount;
|
||||
}
|
||||
|
||||
public String getEncode() {
|
||||
return encode;
|
||||
}
|
||||
|
||||
public String getLanguagePackName() {
|
||||
return languagePackName;
|
||||
}
|
||||
|
||||
public String getTextWrap() {
|
||||
return textWrap;
|
||||
@ -317,4 +76,12 @@ public class LocalizationConfig {
|
||||
this.textWrap = textWrap;
|
||||
properties.setProperty(TEXT_WRAP, textWrap);
|
||||
}
|
||||
|
||||
private void setLanguage(String language) {
|
||||
this.language = language;
|
||||
}
|
||||
|
||||
public String getLanguage() {
|
||||
return this.language;
|
||||
}
|
||||
}
|
||||
|
||||
119
src/main/java/org/jcnc/jnotepad/app/i18n/UIResourceBundle.java
Normal file
119
src/main/java/org/jcnc/jnotepad/app/i18n/UIResourceBundle.java
Normal file
@ -0,0 +1,119 @@
|
||||
package org.jcnc.jnotepad.app.i18n;
|
||||
|
||||
import javafx.beans.binding.StringBinding;
|
||||
import javafx.beans.property.ObjectProperty;
|
||||
import javafx.beans.property.SimpleObjectProperty;
|
||||
import javafx.beans.property.StringProperty;
|
||||
import javafx.beans.value.ChangeListener;
|
||||
import org.jcnc.jnotepad.app.config.LocalizationConfig;
|
||||
|
||||
import java.util.Locale;
|
||||
import java.util.ResourceBundle;
|
||||
|
||||
/**
|
||||
* UI资源绑定,用于加载语言文件。
|
||||
*
|
||||
* @author songdragon
|
||||
*/
|
||||
public class UIResourceBundle {
|
||||
|
||||
private static final UIResourceBundle INSTANCE = new UIResourceBundle();
|
||||
/**
|
||||
* resource目录下的i18n/i18nXXX.properties
|
||||
*/
|
||||
private static final String BASENAME = "i18n/i18n";
|
||||
|
||||
/**
|
||||
* 当前语言
|
||||
*/
|
||||
private Locale currentLocale;
|
||||
|
||||
public static final UIResourceBundle getInstance() {
|
||||
return INSTANCE;
|
||||
}
|
||||
|
||||
private UIResourceBundle() {
|
||||
this.resetLocal();
|
||||
}
|
||||
|
||||
/**
|
||||
* 资源文件的观察者绑定。
|
||||
*/
|
||||
private ObjectProperty<ResourceBundle> resources = new SimpleObjectProperty<>();
|
||||
|
||||
/**
|
||||
* 获取当前资源文件
|
||||
* @return
|
||||
*/
|
||||
public ObjectProperty<ResourceBundle> resourcesProperty() {
|
||||
return resources;
|
||||
}
|
||||
|
||||
public final ResourceBundle getResources() {
|
||||
return resourcesProperty().get();
|
||||
}
|
||||
|
||||
public final void setResources(ResourceBundle resources) {
|
||||
resourcesProperty().set(resources);
|
||||
}
|
||||
|
||||
/**
|
||||
* 重置当前local
|
||||
*/
|
||||
public final void resetLocal() {
|
||||
if (this.currentLocale == LocalizationConfig.getCurrentLocal()) {
|
||||
return;
|
||||
}
|
||||
this.currentLocale = LocalizationConfig.getCurrentLocal();
|
||||
ResourceBundle resourceBundle = ResourceBundle.getBundle(BASENAME, currentLocale);
|
||||
this.setResources(resourceBundle);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取key对应的绑定属性内容
|
||||
* @param key key
|
||||
* @return key对应的内容
|
||||
*/
|
||||
public StringBinding getStringBinding(String key) {
|
||||
return new StringBinding() {
|
||||
{
|
||||
bind(resourcesProperty());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String computeValue() {
|
||||
return getResources().getString(key);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* 工具方法:绑定StringProperty和Key对应的内容
|
||||
* @param stringProperty
|
||||
* @param key
|
||||
*/
|
||||
public static void bindStringProperty(StringProperty stringProperty, String key) {
|
||||
if (stringProperty == null) {
|
||||
return;
|
||||
}
|
||||
stringProperty.bind(getInstance().getStringBinding(key));
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取当前资源中的key值
|
||||
* @param key
|
||||
* @return
|
||||
*/
|
||||
public static String getContent(String key) {
|
||||
return getInstance().getResources().getString(key);
|
||||
}
|
||||
|
||||
/**
|
||||
* 注册资源变更监听器
|
||||
* @param listener
|
||||
*/
|
||||
public void addListener(ChangeListener<? super ResourceBundle> listener) {
|
||||
this.resources.addListener(listener);
|
||||
}
|
||||
}
|
||||
@ -85,7 +85,6 @@ public abstract class LoadJnotepadConfig<T> {
|
||||
} catch (IOException e) {
|
||||
PopUpUtil.errorAlert("错误", "读写错误", "配置文件读写错误!");
|
||||
}
|
||||
LocalizationConfig.getLocalizationConfig().initLocalizationConfig();
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -8,8 +8,6 @@ import org.slf4j.Logger;
|
||||
|
||||
import java.io.InputStream;
|
||||
|
||||
import static org.jcnc.jnotepad.constants.TextConstants.LANGUAGE_FILE_MAP;
|
||||
|
||||
/**
|
||||
* 加载语言配置文件
|
||||
*
|
||||
@ -31,12 +29,10 @@ public class LoadLanguageConfig extends LoadJnotepadConfig<String> {
|
||||
String language = parseConfig(inputStream);
|
||||
if (!"".equals(language) && language != null) {
|
||||
log.info("正在加载语言包:{}", language);
|
||||
localizationConfig.setLanguagePackName(LANGUAGE_FILE_MAP.get(language));
|
||||
// 刷新语言包
|
||||
localizationConfig.initLocalizationConfig();
|
||||
localizationConfig.setCurrentLocal(language);
|
||||
JNotepadMenuBar jNotepadMenuBar = JNotepadMenuBar.getMenuBar();
|
||||
// 刷新菜单栏
|
||||
jNotepadMenuBar.initMenuBar();
|
||||
jNotepadMenuBar.toggleLanguageCheck(language);
|
||||
JNotepadStatusBox.getInstance().initStatusBox();
|
||||
}
|
||||
|
||||
@ -10,14 +10,8 @@ import org.jcnc.jnotepad.json.DataGenerator;
|
||||
import org.jcnc.jnotepad.json.MyData;
|
||||
import org.jcnc.jnotepad.tool.JsonUtil;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 文本常量
|
||||
* <p>
|
||||
* 任何string请都在此处readPropertiesFromFile,然后在
|
||||
* src/main/java/org/jcnc/jnotepad/init/Config.java的getXXXXXLanguagePack
|
||||
* 注册配置文件,设置多语言语言包
|
||||
* 文本常量,被多处使用的常量放到此处。如果只有一个class使用,在class中使用private static final声明。
|
||||
*
|
||||
* @author gewuyou
|
||||
*/
|
||||
@ -57,22 +51,12 @@ public class TextConstants {
|
||||
public static final String ENCODE = "ENCODE";
|
||||
|
||||
/// Config 文本常量
|
||||
|
||||
public static final String CH_LANGUAGE_PACK_NAME = "ch_language_pack.txt";
|
||||
public static final String EN_LANGUAGE_PACK_NAME = "en_language_pack.txt";
|
||||
|
||||
public static final String ENGLISH = "english";
|
||||
|
||||
public static final String CHINESE = "chinese";
|
||||
|
||||
public static final String LOWER_LANGUAGE = "language";
|
||||
/**
|
||||
* 语言映射
|
||||
*/
|
||||
public static final Map<String, String> LANGUAGE_FILE_MAP = Map.of(
|
||||
CHINESE, CH_LANGUAGE_PACK_NAME,
|
||||
ENGLISH, EN_LANGUAGE_PACK_NAME
|
||||
);
|
||||
|
||||
/// 配置文件文本常量
|
||||
/**
|
||||
* 内置配置文件
|
||||
|
||||
@ -3,6 +3,8 @@ package org.jcnc.jnotepad.controller.event.handler;
|
||||
import javafx.event.ActionEvent;
|
||||
import javafx.event.EventHandler;
|
||||
import org.jcnc.jnotepad.app.config.LocalizationConfig;
|
||||
import org.jcnc.jnotepad.app.i18n.UIResourceBundle;
|
||||
import org.jcnc.jnotepad.constants.TextConstants;
|
||||
import org.jcnc.jnotepad.ui.LineNumberTextArea;
|
||||
import org.jcnc.jnotepad.ui.status.JNotepadStatusBox;
|
||||
import org.jcnc.jnotepad.ui.tab.JNotepadTab;
|
||||
@ -20,7 +22,6 @@ import org.jcnc.jnotepad.view.manager.ViewManager;
|
||||
public class NewFile implements EventHandler<ActionEvent> {
|
||||
|
||||
/**
|
||||
*
|
||||
* 处理新建文件事件。
|
||||
*
|
||||
* @param event 事件对象
|
||||
@ -34,7 +35,7 @@ public class NewFile implements EventHandler<ActionEvent> {
|
||||
// TODO: refactor:统一TextArea新建、绑定监听器入口
|
||||
ViewManager viewManager = ViewManager.getInstance();
|
||||
// 将Tab页添加到TabPane中
|
||||
JNotepadTabPane.getInstance().addNewTab(new JNotepadTab(LocalizationConfig.getLocalizationConfig().getNewFile()
|
||||
JNotepadTabPane.getInstance().addNewTab(new JNotepadTab(UIResourceBundle.getContent(TextConstants.NEW_FILE)
|
||||
+ viewManager.selfIncreaseAndGetTabIndex(),
|
||||
textArea));
|
||||
|
||||
|
||||
@ -4,6 +4,8 @@ import javafx.application.Platform;
|
||||
import javafx.concurrent.Task;
|
||||
import org.jcnc.jnotepad.Interface.ControllerInterface;
|
||||
import org.jcnc.jnotepad.app.config.LocalizationConfig;
|
||||
import org.jcnc.jnotepad.app.i18n.UIResourceBundle;
|
||||
import org.jcnc.jnotepad.constants.TextConstants;
|
||||
import org.jcnc.jnotepad.manager.ThreadPoolManager;
|
||||
import org.jcnc.jnotepad.tool.EncodingDetector;
|
||||
import org.jcnc.jnotepad.tool.LogUtil;
|
||||
@ -114,7 +116,7 @@ public class Controller implements ControllerInterface {
|
||||
@Override
|
||||
public void updateUiWithNewTextArea(LineNumberTextArea textArea) {
|
||||
ViewManager viewManager = ViewManager.getInstance();
|
||||
String tabTitle = LocalizationConfig.getLocalizationConfig().getNewFile() + viewManager.selfIncreaseAndGetTabIndex();
|
||||
String tabTitle = UIResourceBundle.getContent(TextConstants.NEW_FILE) + viewManager.selfIncreaseAndGetTabIndex();
|
||||
JNotepadTabPane.getInstance().addNewTab(new JNotepadTab(tabTitle, textArea));
|
||||
}
|
||||
|
||||
|
||||
@ -41,11 +41,11 @@ public class EncodingDetector {
|
||||
charsetDetector.setText(inputStream);
|
||||
CharsetMatch[] matchList = charsetDetector.detectAll();
|
||||
if (matchList == null || matchList.length == 0) {
|
||||
return localizationConfig.getUnknown();
|
||||
return null;
|
||||
}
|
||||
CharsetMatch maxConfidence = matchList[0];
|
||||
if (maxConfidence.getConfidence() < THRESHOLD_CONFIDENCE) {
|
||||
return localizationConfig.getUnknown();
|
||||
return null;
|
||||
}
|
||||
for (int i = 1; i < matchList.length; i++) {
|
||||
CharsetMatch match = matchList[i];
|
||||
@ -59,7 +59,7 @@ public class EncodingDetector {
|
||||
} catch (Exception e) {
|
||||
LOG.error("", e);
|
||||
}
|
||||
return localizationConfig.getUnknown();
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@ -8,6 +8,8 @@ import javafx.stage.Stage;
|
||||
import org.jcnc.jnotepad.LunchApp;
|
||||
import org.jcnc.jnotepad.app.config.GlobalConfig;
|
||||
import org.jcnc.jnotepad.app.config.LocalizationConfig;
|
||||
import org.jcnc.jnotepad.app.i18n.UIResourceBundle;
|
||||
import org.jcnc.jnotepad.constants.TextConstants;
|
||||
import org.jcnc.jnotepad.controller.event.handler.*;
|
||||
import org.jcnc.jnotepad.exception.AppException;
|
||||
import org.jcnc.jnotepad.tool.JsonUtil;
|
||||
@ -20,6 +22,7 @@ import org.slf4j.Logger;
|
||||
import java.io.*;
|
||||
import java.nio.charset.Charset;
|
||||
import java.util.HashMap;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
|
||||
import static com.fasterxml.jackson.core.JsonEncoding.UTF8;
|
||||
@ -44,7 +47,7 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
Logger logger = LogUtil.getLogger(this.getClass());
|
||||
|
||||
private JNotepadMenuBar() {
|
||||
|
||||
initMenuBar();
|
||||
}
|
||||
|
||||
/**
|
||||
@ -148,16 +151,21 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
* 初始化语言菜单
|
||||
*/
|
||||
private void initLanguageMenu() {
|
||||
logger.info("初始化语言菜单:{}", localizationConfig.getLanguage());
|
||||
logger.info("初始化语言菜单:{}", UIResourceBundle.getContent(LANGUAGE));
|
||||
// 语言菜单
|
||||
languageMenu = new Menu(localizationConfig.getLanguage());
|
||||
languageMenu = new Menu();
|
||||
UIResourceBundle.bindStringProperty(languageMenu.textProperty(), LANGUAGE);
|
||||
ToggleGroup languageToggleGroup = new ToggleGroup();
|
||||
|
||||
chineseItem = new RadioMenuItem(localizationConfig.getChinese());
|
||||
chineseItem = new RadioMenuItem();
|
||||
UIResourceBundle.bindStringProperty(chineseItem.textProperty(), UPPER_CHINESE);
|
||||
chineseItem.setUserData(Locale.CHINESE);
|
||||
itemMap.put("chineseItem", chineseItem);
|
||||
languageToggleGroup.getToggles().add(chineseItem);
|
||||
|
||||
englishItem = new RadioMenuItem(localizationConfig.getEnglish());
|
||||
englishItem = new RadioMenuItem();
|
||||
UIResourceBundle.bindStringProperty(englishItem.textProperty(), UPPER_ENGLISH);
|
||||
englishItem.setUserData(Locale.ENGLISH);
|
||||
itemMap.put("englishItem", englishItem);
|
||||
languageToggleGroup.getToggles().add(englishItem);
|
||||
|
||||
@ -169,20 +177,26 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
* 初始化文件菜单
|
||||
*/
|
||||
private void initFileMenu() {
|
||||
logger.info("初始化文件菜单:{}", localizationConfig.getFile());
|
||||
logger.info("初始化文件菜单:{}", UIResourceBundle.getContent(FILE));
|
||||
// 文件菜单
|
||||
fileMenu = new Menu(localizationConfig.getFile());
|
||||
fileMenu = new Menu();
|
||||
UIResourceBundle.bindStringProperty(fileMenu.textProperty(), FILE);
|
||||
|
||||
newItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(newItem.textProperty(), NEW);
|
||||
|
||||
newItem = new MenuItem(localizationConfig.getNewly());
|
||||
itemMap.put("newItem", newItem);
|
||||
|
||||
openItem = new MenuItem(localizationConfig.getOpen());
|
||||
openItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(openItem.textProperty(), OPEN);
|
||||
itemMap.put("openItem", openItem);
|
||||
|
||||
saveItem = new MenuItem(localizationConfig.getSava());
|
||||
saveItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(saveItem.textProperty(), SAVE);
|
||||
itemMap.put("saveItem", saveItem);
|
||||
|
||||
saveAsItem = new MenuItem(localizationConfig.getSavaAs());
|
||||
saveAsItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(saveAsItem.textProperty(), SAVE_AS);
|
||||
itemMap.put("saveAsItem", saveAsItem);
|
||||
|
||||
fileMenu.getItems().addAll(newItem, openItem, saveItem, saveAsItem);
|
||||
@ -192,18 +206,22 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
* 初始化设置菜单
|
||||
*/
|
||||
private void initSettingMenu() {
|
||||
logger.info("初始化设置菜单:{}", localizationConfig.getSet());
|
||||
logger.info("初始化设置菜单:{}", UIResourceBundle.getContent(SET));
|
||||
// 设置菜单
|
||||
setMenu = new Menu(localizationConfig.getSet());
|
||||
setMenu = new Menu();
|
||||
UIResourceBundle.bindStringProperty(setMenu.textProperty(), SET);
|
||||
|
||||
lineFeedItem = new CheckMenuItem(localizationConfig.getWordWrap());
|
||||
lineFeedItem = new CheckMenuItem();
|
||||
UIResourceBundle.bindStringProperty(lineFeedItem.textProperty(), WORD_WRAP);
|
||||
itemMap.put("lineFeedItem", lineFeedItem);
|
||||
lineFeedItem.selectedProperty().set(true);
|
||||
|
||||
topItem = new CheckMenuItem(localizationConfig.getTop());
|
||||
topItem = new CheckMenuItem();
|
||||
UIResourceBundle.bindStringProperty(topItem.textProperty(), TOP);
|
||||
itemMap.put("topItem", topItem);
|
||||
|
||||
openConfigItem = new MenuItem(localizationConfig.getOpenConfigurationFile());
|
||||
openConfigItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(openConfigItem.textProperty(), OPEN_CONFIGURATION_FILE);
|
||||
itemMap.put("openConfigItem", openConfigItem);
|
||||
|
||||
itemMap.put("languageMenu", languageMenu);
|
||||
@ -214,13 +232,17 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
* 初始化插件菜单
|
||||
*/
|
||||
private void initPluginMenu() {
|
||||
logger.info("初始化插件菜单:{}", localizationConfig.getPlugin());
|
||||
logger.info("初始化插件菜单:{}", UIResourceBundle.getContent(PLUGIN));
|
||||
// 插件菜单
|
||||
pluginMenu = new Menu(localizationConfig.getPlugin());
|
||||
addItem = new MenuItem(localizationConfig.getAddPlugin());
|
||||
pluginMenu = new Menu();
|
||||
UIResourceBundle.bindStringProperty(pluginMenu.textProperty(), PLUGIN);
|
||||
|
||||
addItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(addItem.textProperty(), ADD_PLUGIN);
|
||||
itemMap.put("addItem", addItem);
|
||||
|
||||
countItem = new MenuItem(localizationConfig.getStatistics());
|
||||
countItem = new MenuItem();
|
||||
UIResourceBundle.bindStringProperty(countItem.textProperty(), STATISTICS);
|
||||
itemMap.put("countItem", countItem);
|
||||
|
||||
pluginMenu.getItems().addAll(addItem, countItem);
|
||||
@ -254,8 +276,10 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
englishItem.setOnAction(new LocalizationHandler() {
|
||||
@Override
|
||||
public void handle(ActionEvent actionEvent) {
|
||||
|
||||
try {
|
||||
setCurrentLanguage(ENGLISH);
|
||||
toggleLanguage(actionEvent);
|
||||
|
||||
} catch (JsonProcessingException e) {
|
||||
throw new AppException(e.getMessage());
|
||||
@ -267,7 +291,7 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
public void handle(ActionEvent actionEvent) {
|
||||
try {
|
||||
setCurrentLanguage(CHINESE);
|
||||
|
||||
toggleLanguage(actionEvent);
|
||||
} catch (JsonProcessingException e) {
|
||||
throw new AppException(e.getMessage());
|
||||
}
|
||||
@ -275,6 +299,17 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
});
|
||||
}
|
||||
|
||||
private void toggleLanguage(ActionEvent actionEvent) {
|
||||
if (actionEvent == null) {
|
||||
return;
|
||||
}
|
||||
RadioMenuItem languageItem = (RadioMenuItem) actionEvent.getSource();
|
||||
if (languageItem == null) {
|
||||
return;
|
||||
}
|
||||
LocalizationConfig.setCurrentLocal((Locale) languageItem.getUserData());
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置当前语言<br>
|
||||
*
|
||||
@ -283,7 +318,7 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
*/
|
||||
private void setCurrentLanguage(String language) throws JsonProcessingException {
|
||||
// 如果当前已是该语言则不执行该方法
|
||||
if (localizationConfig.getLanguagePackName().equals(LANGUAGE_FILE_MAP.get(language))) {
|
||||
if (localizationConfig.getLanguage().equals(language)) {
|
||||
return;
|
||||
}
|
||||
boolean flag = false;
|
||||
@ -315,7 +350,7 @@ public class JNotepadMenuBar extends MenuBar {
|
||||
writer.write(JsonUtil.toJsonString(json));
|
||||
// 刷新文件
|
||||
writer.flush();
|
||||
// 重新加载语言包和快捷键
|
||||
// 重新加载快捷键
|
||||
View.getInstance().initJnotepadConfigs(LunchApp.getLocalizationConfigs());
|
||||
logger.info("已刷新语言包!");
|
||||
logger.info("已刷新快捷键!");
|
||||
|
||||
@ -1,14 +1,19 @@
|
||||
package org.jcnc.jnotepad.ui.status;
|
||||
|
||||
import javafx.beans.value.ChangeListener;
|
||||
import javafx.beans.value.ObservableValue;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.control.TextArea;
|
||||
import javafx.scene.layout.HBox;
|
||||
import org.jcnc.jnotepad.app.config.LocalizationConfig;
|
||||
import org.jcnc.jnotepad.app.i18n.UIResourceBundle;
|
||||
import org.jcnc.jnotepad.constants.TextConstants;
|
||||
import org.jcnc.jnotepad.ui.tab.JNotepadTab;
|
||||
import org.jcnc.jnotepad.ui.tab.JNotepadTabPane;
|
||||
|
||||
import java.nio.charset.Charset;
|
||||
import java.util.ResourceBundle;
|
||||
|
||||
/**
|
||||
* 状态栏组件封装。
|
||||
@ -20,16 +25,19 @@ import java.nio.charset.Charset;
|
||||
public class JNotepadStatusBox extends HBox {
|
||||
|
||||
private static final JNotepadStatusBox STATUS_BOX = new JNotepadStatusBox();
|
||||
LocalizationConfig localizationConfig = LocalizationConfig.getLocalizationConfig();
|
||||
/**
|
||||
* 字数统计及光标
|
||||
*/
|
||||
private Label statusLabel;
|
||||
private static final String STATUS_LABEL_FORMAT = "%s : %d \t%s: %d \t%s: %d \t";
|
||||
|
||||
|
||||
/**
|
||||
* 显示文本编码
|
||||
*/
|
||||
private Label enCodingLabel;
|
||||
private Label encodingLabel;
|
||||
private final String ENCODING_LABEL_FORMAT = "\t%s : %s";
|
||||
|
||||
|
||||
private JNotepadStatusBox() {
|
||||
initStatusBox();
|
||||
@ -43,14 +51,23 @@ public class JNotepadStatusBox extends HBox {
|
||||
public void initStatusBox() {
|
||||
this.getChildren().clear();
|
||||
// 创建状态栏
|
||||
statusLabel = new Label(localizationConfig.getRow() + ":1 \t" + localizationConfig.getColumn() + ":1 \t" + localizationConfig.getWordCount() + ":0 ");
|
||||
statusLabel = new Label();
|
||||
statusLabel.setText(getStatusBarFormattedText(0, 0, 1));
|
||||
// 创建新的标签以显示编码信息
|
||||
enCodingLabel = new Label();
|
||||
encodingLabel = new Label();
|
||||
updateEncodingLabel();
|
||||
updateWhenTabSelected();
|
||||
this.getChildren().add(statusLabel);
|
||||
this.getChildren().add(enCodingLabel);
|
||||
this.getChildren().add(encodingLabel);
|
||||
this.getProperties().put("borderpane-margin", new Insets(5, 10, 5, 10));
|
||||
|
||||
UIResourceBundle.getInstance().addListener(new ChangeListener<ResourceBundle>() {
|
||||
@Override
|
||||
public void changed(ObservableValue<? extends ResourceBundle> observable, ResourceBundle oldValue, ResourceBundle newValue) {
|
||||
updateWhenTabSelected();
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
public static JNotepadStatusBox getInstance() {
|
||||
@ -70,7 +87,7 @@ public class JNotepadStatusBox extends HBox {
|
||||
if (encoding == null) {
|
||||
encoding = Charset.defaultCharset().name();
|
||||
}
|
||||
this.enCodingLabel.setText("\t" + localizationConfig.getEncode() + ": " + encoding);
|
||||
this.encodingLabel.setText(getEncodingFormattedText(encoding));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -86,7 +103,7 @@ public class JNotepadStatusBox extends HBox {
|
||||
int row = getRow(caretPosition, textArea.getText());
|
||||
int column = getColumn(caretPosition, textArea.getText());
|
||||
int length = textArea.getLength();
|
||||
this.statusLabel.setText(localizationConfig.getRow() + ": " + row + " \t" + localizationConfig.getColumn() + ": " + column + " \t" + localizationConfig.getWordCount() + ": " + length);
|
||||
this.statusLabel.setText(getStatusBarFormattedText(row, column, length));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -135,4 +152,21 @@ public class JNotepadStatusBox extends HBox {
|
||||
return caretPosition - text.lastIndexOf("\n", caretPosition - 1);
|
||||
}
|
||||
|
||||
protected String getStatusBarFormattedText(int row, int column, int wordCount) {
|
||||
String rowText = UIResourceBundle.getContent(TextConstants.ROW);
|
||||
String columnText = UIResourceBundle.getContent(TextConstants.COLUMN);
|
||||
String wordCountText = UIResourceBundle.getContent(TextConstants.WORD_COUNT);
|
||||
return String.format(STATUS_LABEL_FORMAT,
|
||||
rowText,
|
||||
row,
|
||||
columnText,
|
||||
column,
|
||||
wordCountText,
|
||||
wordCount
|
||||
);
|
||||
}
|
||||
|
||||
protected String getEncodingFormattedText(String encoding) {
|
||||
return String.format(ENCODING_LABEL_FORMAT, UIResourceBundle.getContent(TextConstants.ENCODE), encoding);
|
||||
}
|
||||
}
|
||||
|
||||
21
src/main/resources/i18n/i18n.properties
Normal file
21
src/main/resources/i18n/i18n.properties
Normal file
@ -0,0 +1,21 @@
|
||||
LANGUAGE=语言
|
||||
NEW_FILE=新建文件
|
||||
NEW=新建
|
||||
SET=设置
|
||||
ENGLISH=英文
|
||||
STATISTICS=统计字数
|
||||
COLUMN=列数
|
||||
PLUGIN=插件
|
||||
CHINESE=中文
|
||||
title=JNotepad
|
||||
OPEN=打开
|
||||
OPEN_CONFIGURATION_FILE=打开配置文件
|
||||
TOP=窗口置顶
|
||||
WORD_WRAP=自动换行
|
||||
WORD_COUNT=字数
|
||||
SAVE_AS=另存为
|
||||
SAVE=保存
|
||||
ROW=行数
|
||||
FILE=文件
|
||||
ADD_PLUGIN=增加插件
|
||||
ENCODE=编码
|
||||
21
src/main/resources/i18n/i18n_en.properties
Normal file
21
src/main/resources/i18n/i18n_en.properties
Normal file
@ -0,0 +1,21 @@
|
||||
LANGUAGE=Language
|
||||
NEW=New
|
||||
NEW_FILE=New File
|
||||
SET=Settings
|
||||
ENGLISH=English
|
||||
STATISTICS=Word Count
|
||||
COLUMN=Column
|
||||
PLUGIN=Plugins
|
||||
CHINESE=Chinese
|
||||
title=JNotepad
|
||||
OPEN=Open
|
||||
OPEN_CONFIGURATION_FILE=Open Configuration File
|
||||
TOP=Window Top
|
||||
WORD_WRAP=Word Wrap
|
||||
WORD_COUNT=Word Count
|
||||
SAVE_AS=Save As
|
||||
SAVE=Save
|
||||
ROW=Row
|
||||
FILE=File
|
||||
ADD_PLUGIN=Add Plugin
|
||||
ENCODE=Encoding
|
||||
21
src/main/resources/i18n/i18n_zh_CN.properties
Normal file
21
src/main/resources/i18n/i18n_zh_CN.properties
Normal file
@ -0,0 +1,21 @@
|
||||
LANGUAGE=语言
|
||||
NEW_FILE=新建文件
|
||||
NEW=新建
|
||||
SET=设置
|
||||
ENGLISH=英文
|
||||
STATISTICS=统计字数
|
||||
COLUMN=列数
|
||||
PLUGIN=插件
|
||||
CHINESE=中文
|
||||
title=JNotepad
|
||||
OPEN=打开
|
||||
OPEN_CONFIGURATION_FILE=打开配置文件
|
||||
TOP=窗口置顶
|
||||
WORD_WRAP=自动换行
|
||||
WORD_COUNT=字数
|
||||
SAVE_AS=另存为
|
||||
SAVE=保存
|
||||
ROW=行数
|
||||
FILE=文件
|
||||
ADD_PLUGIN=增加插件
|
||||
ENCODE=编码
|
||||
Loading…
x
Reference in New Issue
Block a user