diff --git a/lib/gui/app/i18n.ts b/lib/gui/app/i18n.ts
index debb9430..c7c7e83a 100644
--- a/lib/gui/app/i18n.ts
+++ b/lib/gui/app/i18n.ts
@@ -1,317 +1,36 @@
import i18next from 'i18next';
import { initReactI18next } from 'react-i18next';
+import zh_CN_translation from './i18n/zh-CN';
+import zh_TW_translation from './i18n/zh-TW';
+import en_translation from './i18n/en';
-let lang = Intl.DateTimeFormat().resolvedOptions().locale;
-lang = lang.substr(0, 2);
+export function langParser() {
+ const lang = Intl.DateTimeFormat().resolvedOptions().locale;
+
+ switch (lang.substr(0, 2)) {
+ case 'zh':
+ if (lang === 'zh-CN' || lang === 'zh-SG') {
+ return 'zh-CN';
+ } // Simplified Chinese
+ else {
+ return 'zh-TW';
+ } // Traditional Chinese
+ default:
+ return lang.substr(0, 2);
+ }
+}
i18next.use(initReactI18next).init({
- lng: lang,
+ lng: langParser(),
fallbackLng: 'en',
+ nonExplicitSupportedLngs: true,
interpolation: {
escapeValue: false,
},
resources: {
- zh: {
- translation: {
- ok: '好',
- cancel: '取消',
- continue: '继续',
- skip: '跳过',
- sure: '我确定',
- warning: '请注意!',
- attention: '请注意',
- failed: '失败',
- completed: '完毕',
- yesExit: '是的,可以退出',
- reallyExit: '真的要现在退出 Etcher 吗?',
- yesContinue: '是的,继续',
- progress: {
- starting: '正在启动……',
- decompressing: '正在解压……',
- flashing: '正在烧录……',
- finishing: '正在结束……',
- verifying: '正在验证……',
- failing: '失败……',
- },
- message: {
- sizeNotRecommended: '大小不推荐',
- tooSmall: '空间太小',
- locked: '被锁定',
- system: '系统盘',
- containsImage: '存放源镜像',
- largeDrive: '很大的磁盘',
- sourceLarger: '所选的镜像比目标盘大了 {{byte}} 比特。',
- flashSucceed_one: '烧录成功',
- flashSucceed_other: '烧录成功',
- flashFail_one: '烧录失败',
- flashFail_other: '烧录失败',
- to: '到 ',
- andFail: '并烧录失败了 ',
- target_one: ' 个目标',
- target_other: ' 个目标',
- succeedTo: '被成功烧录',
- exitWhileFlashing:
- '您当前正在刷机。 关闭 Etcher 可能会导致您的磁盘无法使用。',
- looksLikeWindowsImage:
- '看起来您正在尝试刻录 Windows 镜像。\n\n与其他镜像不同,Windows 镜像需要特殊处理才能使其可启动。 我们建议您使用专门为此目的设计的工具,例如 Rufus (Windows)、WoeUSB (Linux) 或 Boot Camp 助理 (macOS)。',
- missingPartitionTable:
- '看起来这不是一个可启动的镜像。\n\n这个镜像似乎不包含分区表,因此您的设备可能无法识别或无法正确启动。',
- driveMissingPartitionTable:
- '看起来这不是可引导磁盘。\n这个磁盘似乎不包含分区表,\n因此您的设备可能无法识别或无法正确启动。',
- largeDriveSize:
- '这是个很大的磁盘!请检查并确认它不包含对您很重要的信息',
- systemDrive: '选择系统盘很危险,因为这将会删除你的系统',
- sourceDrive: '源镜像位于这个分区中',
- noSpace: '磁盘空间不足。 请插入另一个较大的磁盘并重试。',
- genericFlashError:
- '出了点问题。如果源镜像曾被压缩过,请检查它是否已损坏。',
- validation:
- '写入已成功完成,但 Etcher 在从磁盘读取镜像时检测到潜在的损坏问题。 \n\n请考虑将镜像写入其他磁盘。',
- openError: '打开 {{source}} 时出错。\n\n错误信息: {{error}}',
- flashError: '烧录 {{image}} 到 {{target}} 失败。',
- unplug:
- '看起来 Etcher 失去了对磁盘的连接。 它是不是被意外拔掉了?\n\n有时这个错误是因为读卡器出了故障。',
- cannotWrite:
- '看起来 Etcher 无法写入磁盘的这个位置。 此错误通常是由故障的磁盘、读取器或端口引起的。 \n\n请使用其他磁盘、读卡器或端口重试。',
- childWriterDied:
- '写入进程意外崩溃。请再试一次,如果问题仍然存在,请联系 Etcher 团队。',
- badProtocol: '仅支持 http:// 和 https:// 开头的网址。',
- },
- target: {
- selectTarget: '选择目标磁盘',
- plugTarget: '请插入目标磁盘',
- targets: '个目标',
- change: '更改',
- },
- menu: {
- edit: '编辑',
- view: '视图',
- devTool: '打开开发者工具',
- window: '窗口',
- help: '帮助',
- pro: 'Etcher 专业版',
- website: 'Etcher 的官网',
- issue: '提交一个 issue',
- about: '关于 Etcher',
- hide: '隐藏 Etcher',
- hideOthers: '隐藏其它窗口',
- unhide: '取消隐藏',
- quit: '退出 Etcher',
- },
- source: {
- useSourceURL: '使用镜像网络地址',
- auth: '验证',
- username: '输入用户名',
- password: '输入密码',
- unsupportedProtocol: '不支持的协议',
- windowsImage: '这可能是 Windows 系统镜像',
- partitionTable: '找不到分区表',
- errorOpen: '打开源镜像时出错',
- fromFile: '从文件烧录',
- fromURL: '从在线地址烧录',
- clone: '克隆磁盘',
- image: '镜像信息',
- name: '名称:',
- path: '路径:',
- selectSource: '选择源',
- plugSource: '请插入源磁盘',
- osImages: '系统镜像格式',
- allFiles: '任何文件格式',
- enterValidURL: '请输入一个正确的地址',
- },
- drives: {
- name: '名称',
- size: '大小',
- location: '位置',
- find: '找到 {{length}} 个',
- select: '选定 {{select}}',
- showHidden: '显示 {{num}} 个隐藏的磁盘',
- systemDriveDanger: '选择系统盘很危险,因为这将会删除你的系统!',
- openInBrowser: 'Etcher 会在浏览器中打开 {{link}}',
- changeTarget: '改变目标',
- largeDriveWarning: '您即将擦除一个非常大的磁盘',
- largeDriveWarningMsg: '您确定所选磁盘不是存储磁盘吗?',
- systemDriveWarning: '您将要擦除系统盘',
- systemDriveWarningMsg: '您确定要烧录到系统盘吗?',
- },
- flash: {
- another: '烧录另一目标',
- target: '目标',
- location: '位置',
- error: '错误',
- flash: '烧录',
- flashNow: '现在烧录!',
- skip: '跳过了验证',
- moreInfo: '更多信息',
- speedTip:
- '通过将图像大小除以烧录时间来计算速度。\n由于我们能够跳过未使用的部分,因此具有EXT分区的磁盘镜像烧录速度更快。',
- speed: '速度:',
- failedTarget: '失败的烧录目标',
- failedRetry: '重试烧录失败目标',
- },
- settings: {
- errorReporting: '匿名地向 balena.io 报告运行错误和使用统计',
- autoUpdate: '自动更新',
- settings: '软件设置',
- systemInformation: '系统信息',
- },
- },
- },
- en: {
- translation: {
- continue: 'Continue',
- ok: 'OK',
- cancel: 'Cancel',
- skip: 'Skip',
- sure: "Yes, I'm sure",
- warning: 'WARNING! ',
- attention: 'Attention',
- failed: 'Failed',
- completed: 'Completed',
- yesContinue: 'Yes, continue',
- reallyExit: 'Are you sure you want to close Etcher?',
- yesExit: 'Yes, quit',
- progress: {
- starting: 'Starting...',
- decompressing: 'Decompressing...',
- flashing: 'Flashing...',
- finishing: 'Finishing...',
- verifying: 'Verifying...',
- failing: 'Failed',
- },
- message: {
- sizeNotRecommended: 'Not recommended',
- tooSmall: 'Too small',
- locked: 'Locked',
- system: 'System drive',
- containsImage: 'Source drive',
- largeDrive: 'Large drive',
- sourceLarger:
- 'The selected source is {{byte}} larger than this drive.',
- flashSucceed_one: 'Successful target',
- flashSucceed_other: 'Successful targets',
- flashFail_one: 'Failed target',
- flashFail_other: 'Failed targets',
- to: 'to ',
- andFail: 'and failed to be flashed to ',
- target_one: ' target',
- target_other: ' targets',
- succeedTo: 'was successfully flashed',
- exitWhileFlashing:
- 'You are currently flashing a drive. Closing Etcher may leave your drive in an unusable state.',
- looksLikeWindowsImage:
- 'It looks like you are trying to burn a Windows image.\n\nUnlike other images, Windows images require special processing to be made bootable. We suggest you use a tool specially designed for this purpose, such as Rufus (Windows), WoeUSB (Linux), or Boot Camp Assistant (macOS).',
- missingPartitionTable:
- 'It looks like this is not a bootable image.\n\nThe image does not appear to contain a partition table, and might not be recognized or bootable by your device.',
- driveMissingPartitionTable:
- 'It looks like this is not a bootable drive.\nThe drive does not appear to contain a partition table,\nand might not be recognized or bootable by your device.',
- largeDriveSize:
- "This is a large drive! Make sure it doesn't contain files that you want to keep.",
- systemDrive:
- 'Selecting your system drive is dangerous and will erase your drive!',
- sourceDrive: 'Contains the image you chose to flash',
- noSpace:
- 'Not enough space on the drive. Please insert larger one and try again.',
- genericFlashError:
- 'Something went wrong. If it is a compressed image, please check that the archive is not corrupted.',
- validation:
- 'The write has been completed successfully but Etcher detected potential corruption issues when reading the image back from the drive. \n\nPlease consider writing the image to a different drive.',
- openError:
- 'Something went wrong while opening {{source}}.\n\nError: {{error}}',
- flashError:
- 'Something went wrong while writing {{image}} to {{target}}.',
- unplug:
- "Looks like Etcher lost access to the drive. Did it get unplugged accidentally?\n\nSometimes this error is caused by faulty readers that don't provide stable access to the drive.",
- cannotWrite:
- 'Looks like Etcher is not able to write to this location of the drive. This error is usually caused by a faulty drive, reader, or port. \n\nPlease try again with another drive, reader, or port.',
- childWriterDied:
- 'The writer process ended unexpectedly. Please try again, and contact the Etcher team if the problem persists.',
- badProtocol: 'Only http:// and https:// URLs are supported.',
- },
- target: {
- selectTarget: 'Select target',
- plugTarget: 'Plug a target drive',
- targets: 'Targets',
- change: 'Change',
- },
- source: {
- useSourceURL: 'Use Image URL',
- auth: 'Authentication',
- username: 'Enter username',
- password: 'Enter password',
- unsupportedProtocol: 'Unsupported protocol',
- windowsImage: 'Possible Windows image detected',
- partitionTable: 'Missing partition table',
- errorOpen: 'Error opening source',
- fromFile: 'Flash from file',
- fromURL: 'Flash from URL',
- clone: 'Clone drive',
- image: 'Image',
- name: 'Name: ',
- path: 'Path: ',
- selectSource: 'Select source',
- plugSource: 'Plug a source drive',
- osImages: 'OS Images',
- allFiles: 'All',
- enterValidURL: 'Enter a valid URL',
- },
- drives: {
- name: 'Name',
- size: 'Size',
- location: 'Location',
- find: '{{length}} found',
- select: 'Select {{select}}',
- showHidden: 'Show {{num}} hidden',
- systemDriveDanger:
- 'Selecting your system drive is dangerous and will erase your drive!',
- openInBrowser: '`Etcher will open {{link}} in your browser`',
- changeTarget: 'Change target',
- largeDriveWarning: 'You are about to erase an unusually large drive',
- largeDriveWarningMsg:
- 'Are you sure the selected drive is not a storage drive?',
- systemDriveWarning: "You are about to erase your computer's drives",
- systemDriveWarningMsg:
- 'Are you sure you want to flash your system drive?',
- },
- flash: {
- another: 'Flash another',
- target: 'Target',
- location: 'Location',
- error: 'Error',
- flash: 'Flash',
- flashNow: 'Flash!',
- skip: 'Validation has been skipped',
- moreInfo: 'more info',
- speedTip:
- 'The speed is calculated by dividing the image size by the flashing time.\nDisk images with ext partitions flash faster as we are able to skip unused parts.',
- speed: 'Effective speed: ',
- failedTarget: 'Failed targets',
- failedRetry: 'Retry failed targets',
- },
- settings: {
- errorReporting:
- 'Anonymously report errors and usage statistics to balena.io',
- autoUpdate: 'Auto-updates enabled',
- settings: 'Settings',
- systemInformation: 'System Information',
- },
- menu: {
- edit: 'Edit',
- view: 'View',
- devTool: 'Toggle Developer Tools',
- window: 'Window',
- help: 'Help',
- pro: 'Etcher Pro',
- website: 'Etcher Website',
- issue: 'Report an issue',
- about: 'About Etcher',
- hide: 'Hide Etcher',
- hideOthers: 'Hide Others',
- unhide: 'Unhide All',
- quit: 'Quit Etcher',
- },
- },
- },
+ 'zh-CN': zh_CN_translation,
+ 'zh-TW': zh_TW_translation,
+ en: en_translation,
},
});
diff --git a/lib/gui/app/i18n/README.md b/lib/gui/app/i18n/README.md
new file mode 100644
index 00000000..1eb97aac
--- /dev/null
+++ b/lib/gui/app/i18n/README.md
@@ -0,0 +1,23 @@
+# i18n
+
+## How it was done
+
+Using the open-source lib [i18next](https://www.i18next.com/).
+
+## How to add your own language
+
+1. Go to `lib/gui/app/i18n` and add a file named `xx.ts` (use the codes mentioned
+ in [the link](https://www.science.co.il/language/Locale-codes.php), and we support styles as `fr`, `de`, `es-ES`
+ and `pt-BR`)
+ .
+2. Copy the content from an existing translation and start to translate.
+3. Once done, go to `lib/gui/app/i18n.ts` and add a line of `import xx_translation from './i18n/xx'` after the
+ already-added imports and add `xx: xx_translation` in the `resources` section of `i18next.init()` function.
+4. Now go to `lib/shared/catalina-sudo/` and copy the `sudo-askpass.osascript-en.js`, change it to
+ be `sudo-askpass.osascript-xx.js` and edit
+ the `'balenaEtcher needs privileged access in order to flash disks.\n\nType your password to allow this.'` line and
+ those `Ok`s and `Cancel`s to your own language.
+5. If, your language has several variations when they are used in several countries/regions, such as `zh-CN` and `zh-TW`
+ , or `pt-BR` and `pt-PT`, edit
+ the `langParser()` in the `lib/gui/app/i18n.ts` file to meet your need.
+6. Make a commit, and then a pull request on GitHub.
\ No newline at end of file
diff --git a/lib/gui/app/i18n/en.ts b/lib/gui/app/i18n/en.ts
new file mode 100644
index 00000000..a608745c
--- /dev/null
+++ b/lib/gui/app/i18n/en.ts
@@ -0,0 +1,155 @@
+const translation = {
+ translation: {
+ continue: 'Continue',
+ ok: 'OK',
+ cancel: 'Cancel',
+ skip: 'Skip',
+ sure: "Yes, I'm sure",
+ warning: 'WARNING! ',
+ attention: 'Attention',
+ failed: 'Failed',
+ completed: 'Completed',
+ yesContinue: 'Yes, continue',
+ reallyExit: 'Are you sure you want to close Etcher?',
+ yesExit: 'Yes, quit',
+ progress: {
+ starting: 'Starting...',
+ decompressing: 'Decompressing...',
+ flashing: 'Flashing...',
+ finishing: 'Finishing...',
+ verifying: 'Verifying...',
+ failing: 'Failed',
+ },
+ message: {
+ sizeNotRecommended: 'Not recommended',
+ tooSmall: 'Too small',
+ locked: 'Locked',
+ system: 'System drive',
+ containsImage: 'Source drive',
+ largeDrive: 'Large drive',
+ sourceLarger: 'The selected source is {{byte}} larger than this drive.',
+ flashSucceed_one: 'Successful target',
+ flashSucceed_other: 'Successful targets',
+ flashFail_one: 'Failed target',
+ flashFail_other: 'Failed targets',
+ to: 'to ',
+ andFail: 'and failed to be flashed to ',
+ target_one: ' target',
+ target_other: ' targets',
+ succeedTo: 'was successfully flashed',
+ exitWhileFlashing:
+ 'You are currently flashing a drive. Closing Etcher may leave your drive in an unusable state.',
+ looksLikeWindowsImage:
+ 'It looks like you are trying to burn a Windows image.\n\nUnlike other images, Windows images require special processing to be made bootable. We suggest you use a tool specially designed for this purpose, such as Rufus (Windows), WoeUSB (Linux), or Boot Camp Assistant (macOS).',
+ missingPartitionTable:
+ 'It looks like this is not a bootable image.\n\nThe image does not appear to contain a partition table, and might not be recognized or bootable by your device.',
+ driveMissingPartitionTable:
+ 'It looks like this is not a bootable drive.\nThe drive does not appear to contain a partition table,\nand might not be recognized or bootable by your device.',
+ largeDriveSize:
+ "This is a large drive! Make sure it doesn't contain files that you want to keep.",
+ systemDrive:
+ 'Selecting your system drive is dangerous and will erase your drive!',
+ sourceDrive: 'Contains the image you chose to flash',
+ noSpace:
+ 'Not enough space on the drive. Please insert larger one and try again.',
+ genericFlashError:
+ 'Something went wrong. If it is a compressed image, please check that the archive is not corrupted.',
+ validation:
+ 'The write has been completed successfully but Etcher detected potential corruption issues when reading the image back from the drive. \n\nPlease consider writing the image to a different drive.',
+ openError:
+ 'Something went wrong while opening {{source}}.\n\nError: {{error}}',
+ flashError: 'Something went wrong while writing {{image}} to {{target}}.',
+ unplug:
+ "Looks like Etcher lost access to the drive. Did it get unplugged accidentally?\n\nSometimes this error is caused by faulty readers that don't provide stable access to the drive.",
+ cannotWrite:
+ 'Looks like Etcher is not able to write to this location of the drive. This error is usually caused by a faulty drive, reader, or port. \n\nPlease try again with another drive, reader, or port.',
+ childWriterDied:
+ 'The writer process ended unexpectedly. Please try again, and contact the Etcher team if the problem persists.',
+ badProtocol: 'Only http:// and https:// URLs are supported.',
+ },
+ target: {
+ selectTarget: 'Select target',
+ plugTarget: 'Plug a target drive',
+ targets: 'Targets',
+ change: 'Change',
+ },
+ source: {
+ useSourceURL: 'Use Image URL',
+ auth: 'Authentication',
+ username: 'Enter username',
+ password: 'Enter password',
+ unsupportedProtocol: 'Unsupported protocol',
+ windowsImage: 'Possible Windows image detected',
+ partitionTable: 'Missing partition table',
+ errorOpen: 'Error opening source',
+ fromFile: 'Flash from file',
+ fromURL: 'Flash from URL',
+ clone: 'Clone drive',
+ image: 'Image',
+ name: 'Name: ',
+ path: 'Path: ',
+ selectSource: 'Select source',
+ plugSource: 'Plug a source drive',
+ osImages: 'OS Images',
+ allFiles: 'All',
+ enterValidURL: 'Enter a valid URL',
+ },
+ drives: {
+ name: 'Name',
+ size: 'Size',
+ location: 'Location',
+ find: '{{length}} found',
+ select: 'Select {{select}}',
+ showHidden: 'Show {{num}} hidden',
+ systemDriveDanger:
+ 'Selecting your system drive is dangerous and will erase your drive!',
+ openInBrowser: '`Etcher will open {{link}} in your browser`',
+ changeTarget: 'Change target',
+ largeDriveWarning: 'You are about to erase an unusually large drive',
+ largeDriveWarningMsg:
+ 'Are you sure the selected drive is not a storage drive?',
+ systemDriveWarning: "You are about to erase your computer's drives",
+ systemDriveWarningMsg:
+ 'Are you sure you want to flash your system drive?',
+ },
+ flash: {
+ another: 'Flash another',
+ target: 'Target',
+ location: 'Location',
+ error: 'Error',
+ flash: 'Flash',
+ flashNow: 'Flash!',
+ skip: 'Validation has been skipped',
+ moreInfo: 'more info',
+ speedTip:
+ 'The speed is calculated by dividing the image size by the flashing time.\nDisk images with ext partitions flash faster as we are able to skip unused parts.',
+ speed: 'Effective speed: ',
+ failedTarget: 'Failed targets',
+ failedRetry: 'Retry failed targets',
+ },
+ settings: {
+ errorReporting:
+ 'Anonymously report errors and usage statistics to balena.io',
+ autoUpdate: 'Auto-updates enabled',
+ settings: 'Settings',
+ systemInformation: 'System Information',
+ },
+ menu: {
+ edit: 'Edit',
+ view: 'View',
+ devTool: 'Toggle Developer Tools',
+ window: 'Window',
+ help: 'Help',
+ pro: 'Etcher Pro',
+ website: 'Etcher Website',
+ issue: 'Report an issue',
+ about: 'About Etcher',
+ hide: 'Hide Etcher',
+ hideOthers: 'Hide Others',
+ unhide: 'Unhide All',
+ quit: 'Quit Etcher',
+ },
+ },
+};
+
+export default translation;
diff --git a/lib/gui/app/i18n/zh-CN.ts b/lib/gui/app/i18n/zh-CN.ts
new file mode 100644
index 00000000..5c83b33a
--- /dev/null
+++ b/lib/gui/app/i18n/zh-CN.ts
@@ -0,0 +1,147 @@
+const translation = {
+ translation: {
+ ok: '好',
+ cancel: '取消',
+ continue: '继续',
+ skip: '跳过',
+ sure: '我确定',
+ warning: '请注意!',
+ attention: '请注意',
+ failed: '失败',
+ completed: '完毕',
+ yesExit: '是的,可以退出',
+ reallyExit: '真的要现在退出 Etcher 吗?',
+ yesContinue: '是的,继续',
+ progress: {
+ starting: '正在启动……',
+ decompressing: '正在解压……',
+ flashing: '正在烧录……',
+ finishing: '正在结束……',
+ verifying: '正在验证……',
+ failing: '失败……',
+ },
+ message: {
+ sizeNotRecommended: '大小不推荐',
+ tooSmall: '空间太小',
+ locked: '被锁定',
+ system: '系统盘',
+ containsImage: '存放源镜像',
+ largeDrive: '很大的磁盘',
+ sourceLarger: '所选的镜像比目标盘大了 {{byte}} 比特。',
+ flashSucceed_one: '烧录成功',
+ flashSucceed_other: '烧录成功',
+ flashFail_one: '烧录失败',
+ flashFail_other: '烧录失败',
+ to: '到 ',
+ andFail: '并烧录失败了 ',
+ target_one: ' 个目标',
+ target_other: ' 个目标',
+ succeedTo: '被成功烧录',
+ exitWhileFlashing:
+ '您当前正在刷机。 关闭 Etcher 可能会导致您的磁盘无法使用。',
+ looksLikeWindowsImage:
+ '看起来您正在尝试刻录 Windows 镜像。\n\n与其他镜像不同,Windows 镜像需要特殊处理才能使其可启动。 我们建议您使用专门为此目的设计的工具,例如 Rufus (Windows)、WoeUSB (Linux) 或 Boot Camp 助理 (macOS)。',
+ missingPartitionTable:
+ '看起来这不是一个可启动的镜像。\n\n这个镜像似乎不包含分区表,因此您的设备可能无法识别或无法正确启动。',
+ driveMissingPartitionTable:
+ '看起来这不是可引导磁盘。\n这个磁盘似乎不包含分区表,\n因此您的设备可能无法识别或无法正确启动。',
+ largeDriveSize: '这是个很大的磁盘!请检查并确认它不包含对您很重要的信息',
+ systemDrive: '选择系统盘很危险,因为这将会删除你的系统',
+ sourceDrive: '源镜像位于这个分区中',
+ noSpace: '磁盘空间不足。 请插入另一个较大的磁盘并重试。',
+ genericFlashError:
+ '出了点问题。如果源镜像曾被压缩过,请检查它是否已损坏。',
+ validation:
+ '写入已成功完成,但 Etcher 在从磁盘读取镜像时检测到潜在的损坏问题。 \n\n请考虑将镜像写入其他磁盘。',
+ openError: '打开 {{source}} 时出错。\n\n错误信息: {{error}}',
+ flashError: '烧录 {{image}} 到 {{target}} 失败。',
+ unplug:
+ '看起来 Etcher 失去了对磁盘的连接。 它是不是被意外拔掉了?\n\n有时这个错误是因为读卡器出了故障。',
+ cannotWrite:
+ '看起来 Etcher 无法写入磁盘的这个位置。 此错误通常是由故障的磁盘、读取器或端口引起的。 \n\n请使用其他磁盘、读卡器或端口重试。',
+ childWriterDied:
+ '写入进程意外崩溃。请再试一次,如果问题仍然存在,请联系 Etcher 团队。',
+ badProtocol: '仅支持 http:// 和 https:// 开头的网址。',
+ },
+ target: {
+ selectTarget: '选择目标磁盘',
+ plugTarget: '请插入目标磁盘',
+ targets: '个目标',
+ change: '更改',
+ },
+ menu: {
+ edit: '编辑',
+ view: '视图',
+ devTool: '打开开发者工具',
+ window: '窗口',
+ help: '帮助',
+ pro: 'Etcher 专业版',
+ website: 'Etcher 的官网',
+ issue: '提交一个 issue',
+ about: '关于 Etcher',
+ hide: '隐藏 Etcher',
+ hideOthers: '隐藏其它窗口',
+ unhide: '取消隐藏',
+ quit: '退出 Etcher',
+ },
+ source: {
+ useSourceURL: '使用镜像网络地址',
+ auth: '验证',
+ username: '输入用户名',
+ password: '输入密码',
+ unsupportedProtocol: '不支持的协议',
+ windowsImage: '这可能是 Windows 系统镜像',
+ partitionTable: '找不到分区表',
+ errorOpen: '打开源镜像时出错',
+ fromFile: '从文件烧录',
+ fromURL: '从在线地址烧录',
+ clone: '克隆磁盘',
+ image: '镜像信息',
+ name: '名称:',
+ path: '路径:',
+ selectSource: '选择源',
+ plugSource: '请插入源磁盘',
+ osImages: '系统镜像格式',
+ allFiles: '任何文件格式',
+ enterValidURL: '请输入一个正确的地址',
+ },
+ drives: {
+ name: '名称',
+ size: '大小',
+ location: '位置',
+ find: '找到 {{length}} 个',
+ select: '选定 {{select}}',
+ showHidden: '显示 {{num}} 个隐藏的磁盘',
+ systemDriveDanger: '选择系统盘很危险,因为这将会删除你的系统!',
+ openInBrowser: 'Etcher 会在浏览器中打开 {{link}}',
+ changeTarget: '改变目标',
+ largeDriveWarning: '您即将擦除一个非常大的磁盘',
+ largeDriveWarningMsg: '您确定所选磁盘不是存储磁盘吗?',
+ systemDriveWarning: '您将要擦除系统盘',
+ systemDriveWarningMsg: '您确定要烧录到系统盘吗?',
+ },
+ flash: {
+ another: '烧录另一目标',
+ target: '目标',
+ location: '位置',
+ error: '错误',
+ flash: '烧录',
+ flashNow: '现在烧录!',
+ skip: '跳过了验证',
+ moreInfo: '更多信息',
+ speedTip:
+ '通过将图像大小除以烧录时间来计算速度。\n由于我们能够跳过未使用的部分,因此具有EXT分区的磁盘镜像烧录速度更快。',
+ speed: '速度:',
+ failedTarget: '失败的烧录目标',
+ failedRetry: '重试烧录失败目标',
+ },
+ settings: {
+ errorReporting: '匿名地向 balena.io 报告运行错误和使用统计',
+ autoUpdate: '自动更新',
+ settings: '软件设置',
+ systemInformation: '系统信息',
+ },
+ },
+};
+
+export default translation;
diff --git a/lib/gui/app/i18n/zh-TW.ts b/lib/gui/app/i18n/zh-TW.ts
new file mode 100644
index 00000000..21ebf63e
--- /dev/null
+++ b/lib/gui/app/i18n/zh-TW.ts
@@ -0,0 +1,147 @@
+const translation = {
+ translation: {
+ ok: '好',
+ cancel: '取消',
+ continue: '繼續',
+ skip: '跳過',
+ sure: '我確定',
+ warning: '請注意!',
+ attention: '請注意',
+ failed: '失敗',
+ completed: '完畢',
+ yesExit: '是的,可以退出',
+ reallyExit: '真的要現在退出 Etcher 嗎?',
+ yesContinue: '是的,繼續',
+ progress: {
+ starting: '正在啓動……',
+ decompressing: '正在解壓……',
+ flashing: '正在燒錄……',
+ finishing: '正在結束……',
+ verifying: '正在驗證……',
+ failing: '失敗……',
+ },
+ message: {
+ sizeNotRecommended: '大小不推薦',
+ tooSmall: '空間太小',
+ locked: '被鎖定',
+ system: '系統盤',
+ containsImage: '存放源鏡像',
+ largeDrive: '很大的磁盤',
+ sourceLarger: '所選的鏡像比目標盤大了 {{byte}} 比特。',
+ flashSucceed_one: '燒錄成功',
+ flashSucceed_other: '燒錄成功',
+ flashFail_one: '燒錄失敗',
+ flashFail_other: '燒錄失敗',
+ to: '到 ',
+ andFail: '並燒錄失敗了 ',
+ target_one: ' 個目標',
+ target_other: ' 個目標',
+ succeedTo: '被成功燒錄',
+ exitWhileFlashing:
+ '您當前正在刷機。 關閉 Etcher 可能會導致您的磁盤無法使用。',
+ looksLikeWindowsImage:
+ '看起來您正在嘗試刻錄 Windows 鏡像。\n\n與其他鏡像不同,Windows 鏡像需要特殊處理才能使其可啓動。 我們建議您使用專門爲此目的設計的工具,例如 Rufus (Windows)、WoeUSB (Linux) 或 Boot Camp 助理 (macOS)。',
+ missingPartitionTable:
+ '看起來這不是一個可啓動的鏡像。\n\n這個鏡像似乎不包含分區表,因此您的設備可能無法識別或無法正確啓動。',
+ driveMissingPartitionTable:
+ '看起來這不是可引導磁盤。\n這個磁盤似乎不包含分區表,\n因此您的設備可能無法識別或無法正確啓動。',
+ largeDriveSize: '這是個很大的磁盤!請檢查並確認它不包含對您很重要的信息',
+ systemDrive: '選擇系統盤很危險,因爲這將會刪除你的系統',
+ sourceDrive: '源鏡像位於這個分區中',
+ noSpace: '磁盤空間不足。 請插入另一個較大的磁盤並重試。',
+ genericFlashError:
+ '出了點問題。如果源鏡像曾被壓縮過,請檢查它是否已損壞。',
+ validation:
+ '寫入已成功完成,但 Etcher 在從磁盤讀取鏡像時檢測到潛在的損壞問題。 \n\n請考慮將鏡像寫入其他磁盤。',
+ openError: '打開 {{source}} 時出錯。\n\n錯誤信息: {{error}}',
+ flashError: '燒錄 {{image}} 到 {{target}} 失敗。',
+ unplug:
+ '看起來 Etcher 失去了對磁盤的連接。 它是不是被意外拔掉了?\n\n有時這個錯誤是因爲讀卡器出了故障。',
+ cannotWrite:
+ '看起來 Etcher 無法寫入磁盤的這個位置。 此錯誤通常是由故障的磁盤、讀取器或端口引起的。 \n\n請使用其他磁盤、讀卡器或端口重試。',
+ childWriterDied:
+ '寫入進程意外崩潰。請再試一次,如果問題仍然存在,請聯繫 Etcher 團隊。',
+ badProtocol: '僅支持 http:// 和 https:// 開頭的網址。',
+ },
+ target: {
+ selectTarget: '選擇目標磁盤',
+ plugTarget: '請插入目標磁盤',
+ targets: '個目標',
+ change: '更改',
+ },
+ menu: {
+ edit: '編輯',
+ view: '視圖',
+ devTool: '打開開發者工具',
+ window: '窗口',
+ help: '幫助',
+ pro: 'Etcher 專業版',
+ website: 'Etcher 的官網',
+ issue: '提交一個 issue',
+ about: '關於 Etcher',
+ hide: '隱藏 Etcher',
+ hideOthers: '隱藏其它窗口',
+ unhide: '取消隱藏',
+ quit: '退出 Etcher',
+ },
+ source: {
+ useSourceURL: '使用鏡像網絡地址',
+ auth: '驗證',
+ username: '輸入用戶名',
+ password: '輸入密碼',
+ unsupportedProtocol: '不支持的協議',
+ windowsImage: '這可能是 Windows 系統鏡像',
+ partitionTable: '找不到分區表',
+ errorOpen: '打開源鏡像時出錯',
+ fromFile: '從文件燒錄',
+ fromURL: '從在線地址燒錄',
+ clone: '克隆磁盤',
+ image: '鏡像信息',
+ name: '名稱:',
+ path: '路徑:',
+ selectSource: '選擇源',
+ plugSource: '請插入源磁盤',
+ osImages: '系統鏡像格式',
+ allFiles: '任何文件格式',
+ enterValidURL: '請輸入一個正確的地址',
+ },
+ drives: {
+ name: '名稱',
+ size: '大小',
+ location: '位置',
+ find: '找到 {{length}} 個',
+ select: '選定 {{select}}',
+ showHidden: '顯示 {{num}} 個隱藏的磁盤',
+ systemDriveDanger: '選擇系統盤很危險,因爲這將會刪除你的系統!',
+ openInBrowser: 'Etcher 會在瀏覽器中打開 {{link}}',
+ changeTarget: '改變目標',
+ largeDriveWarning: '您即將擦除一個非常大的磁盤',
+ largeDriveWarningMsg: '您確定所選磁盤不是存儲磁盤嗎?',
+ systemDriveWarning: '您將要擦除系統盤',
+ systemDriveWarningMsg: '您確定要燒錄到系統盤嗎?',
+ },
+ flash: {
+ another: '燒錄另一目標',
+ target: '目標',
+ location: '位置',
+ error: '錯誤',
+ flash: '燒錄',
+ flashNow: '現在燒錄!',
+ skip: '跳過了驗證',
+ moreInfo: '更多信息',
+ speedTip:
+ '通過將圖像大小除以燒錄時間來計算速度。\n由於我們能夠跳過未使用的部分,因此具有EXT分區的磁盤鏡像燒錄速度更快。',
+ speed: '速度:',
+ failedTarget: '失敗的燒錄目標',
+ failedRetry: '重試燒錄失敗目標',
+ },
+ settings: {
+ errorReporting: '匿名地向 balena.io 報告運行錯誤和使用統計',
+ autoUpdate: '自動更新',
+ settings: '軟件設置',
+ systemInformation: '系統信息',
+ },
+ },
+};
+
+export default translation;
diff --git a/lib/gui/app/renderer.ts b/lib/gui/app/renderer.ts
index 55c8733f..6c0f8d94 100644
--- a/lib/gui/app/renderer.ts
+++ b/lib/gui/app/renderer.ts
@@ -1,11 +1,10 @@
// @ts-nocheck
import { main } from './app';
import './i18n';
+import { langParser } from './i18n';
import { ipcRenderer } from 'electron';
-let lang = Intl.DateTimeFormat().resolvedOptions().locale;
-lang = lang.substr(0, 2);
-ipcRenderer.send('change-lng', lang);
+ipcRenderer.send('change-lng', langParser());
if (module.hot) {
module.hot.accept('./app', () => {