@sd-angular/core 19.0.0-beta.94 → 19.0.0-beta.95
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -1
- package/components/anchor/src/components/anchor/anchor.component.d.ts +4 -1
- package/components/anchor/src/components/anchor-item/anchor-item.component.d.ts +2 -1
- package/components/anchor/src/components/anchor-vertical/anchor-vertical-list.component.d.ts +3 -1
- package/components/document-builder/src/components/header-footer-builder/header-footer-builder.component.d.ts +2 -2
- package/components/document-builder/src/document-builder.model.d.ts +2 -2
- package/components/editor/src/models/editor.model.d.ts +2 -2
- package/components/editor/src/plugins/image-upload/utils/validate.utils.d.ts +2 -2
- package/components/form-generic/src/components/form-builder/components/attribute-table/attribute-table.component.d.ts +4 -2
- package/components/form-generic/src/components/form-builder/components/attribute-template/attribute-template.component.d.ts +2 -2
- package/components/form-generic/src/components/form-builder/components/configure-validation/configure-validation.component.d.ts +2 -2
- package/components/form-generic/src/components/form-builder/components/group/attribute/group-attribute.component.d.ts +23 -0
- package/components/form-generic/src/components/form-builder/components/group/index.d.ts +1 -0
- package/components/form-generic/src/components/form-builder/components/index.d.ts +1 -0
- package/components/form-generic/src/components/form-builder/components/table/control/table-control.component.d.ts +3 -0
- package/components/form-generic/src/components/form-builder/form-builder.component.d.ts +61 -18
- package/components/form-generic/src/components/form-render/form-render.component.d.ts +2 -2
- package/components/form-generic/src/models/form-generic-component.model.d.ts +22 -2
- package/components/index.d.ts +1 -0
- package/components/modal/src/modal.component.d.ts +4 -1
- package/components/preview/index.d.ts +3 -0
- package/components/preview/src/preview-image/preview-image.component.d.ts +84 -24
- package/components/preview/src/preview-image/preview-image.types.d.ts +53 -0
- package/components/preview/src/preview-pdf/preview-pdf.component.d.ts +186 -0
- package/components/preview/src/preview-pdf/preview-pdf.types.d.ts +84 -0
- package/components/quick-action/src/quick-action.component.d.ts +5 -6
- package/components/table/src/table.component.d.ts +2 -2
- package/components/upload-file/src/upload-file.component.d.ts +4 -1
- package/configurations/src/sd-core.configuration.d.ts +2 -1
- package/fesm2022/sd-angular-core-components-anchor.mjs +19 -6
- package/fesm2022/sd-angular-core-components-anchor.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-button.mjs +1 -1
- package/fesm2022/sd-angular-core-components-button.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-code-editor.mjs +3 -3
- package/fesm2022/sd-angular-core-components-code-editor.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-document-builder.mjs +3 -3
- package/fesm2022/sd-angular-core-components-document-builder.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-editor.mjs +3 -3
- package/fesm2022/sd-angular-core-components-editor.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-form-generic.mjs +627 -317
- package/fesm2022/sd-angular-core-components-form-generic.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-history.mjs +3 -3
- package/fesm2022/sd-angular-core-components-history.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-import-excel.mjs +5 -5
- package/fesm2022/sd-angular-core-components-import-excel.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-modal.mjs +8 -3
- package/fesm2022/sd-angular-core-components-modal.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-preview.mjs +1963 -91
- package/fesm2022/sd-angular-core-components-preview.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-quick-action.mjs +8 -19
- package/fesm2022/sd-angular-core-components-quick-action.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-tab-router.mjs +2 -2
- package/fesm2022/sd-angular-core-components-tab-router.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-table.mjs +32 -29
- package/fesm2022/sd-angular-core-components-table.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components-upload-file.mjs +12 -8
- package/fesm2022/sd-angular-core-components-upload-file.mjs.map +1 -1
- package/fesm2022/sd-angular-core-components.mjs +1 -0
- package/fesm2022/sd-angular-core-components.mjs.map +1 -1
- package/fesm2022/sd-angular-core-configurations.mjs.map +1 -1
- package/fesm2022/sd-angular-core-directives.mjs +2 -2
- package/fesm2022/sd-angular-core-directives.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-autocomplete.mjs +2 -2
- package/fesm2022/sd-angular-core-forms-autocomplete.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-checkbox.mjs +6 -13
- package/fesm2022/sd-angular-core-forms-checkbox.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-chip-calendar.mjs +6 -5
- package/fesm2022/sd-angular-core-forms-chip-calendar.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-chip.mjs +6 -12
- package/fesm2022/sd-angular-core-forms-chip.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-date-range.mjs +33 -26
- package/fesm2022/sd-angular-core-forms-date-range.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-date.mjs +29 -19
- package/fesm2022/sd-angular-core-forms-date.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-datetime.mjs +98 -57
- package/fesm2022/sd-angular-core-forms-datetime.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-input-number.mjs +2 -2
- package/fesm2022/sd-angular-core-forms-input-number.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-input.mjs +5 -5
- package/fesm2022/sd-angular-core-forms-input.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-radio.mjs +7 -15
- package/fesm2022/sd-angular-core-forms-radio.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-select.mjs +4 -4
- package/fesm2022/sd-angular-core-forms-select.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-switch.mjs +6 -14
- package/fesm2022/sd-angular-core-forms-switch.mjs.map +1 -1
- package/fesm2022/sd-angular-core-forms-textarea.mjs +5 -5
- package/fesm2022/sd-angular-core-forms-textarea.mjs.map +1 -1
- package/fesm2022/sd-angular-core-handlers.mjs +2 -2
- package/fesm2022/sd-angular-core-handlers.mjs.map +1 -1
- package/fesm2022/sd-angular-core-i18n.mjs +1575 -38
- package/fesm2022/sd-angular-core-i18n.mjs.map +1 -1
- package/fesm2022/sd-angular-core-interceptors.mjs +2 -2
- package/fesm2022/sd-angular-core-interceptors.mjs.map +1 -1
- package/fesm2022/sd-angular-core-models.mjs +9 -0
- package/fesm2022/sd-angular-core-models.mjs.map +1 -0
- package/fesm2022/sd-angular-core-modules-layout.mjs +87 -39
- package/fesm2022/sd-angular-core-modules-layout.mjs.map +1 -1
- package/fesm2022/sd-angular-core-services-confirm.mjs +2 -2
- package/fesm2022/sd-angular-core-services-confirm.mjs.map +1 -1
- package/fesm2022/sd-angular-core-services-docx.mjs +2 -2
- package/fesm2022/sd-angular-core-services-docx.mjs.map +1 -1
- package/fesm2022/sd-angular-core-services-excel.mjs +27 -23
- package/fesm2022/sd-angular-core-services-excel.mjs.map +1 -1
- package/fesm2022/sd-angular-core-utilities-extensions.mjs +47 -13
- package/fesm2022/sd-angular-core-utilities-extensions.mjs.map +1 -1
- package/fesm2022/sd-angular-core.mjs +0 -1
- package/fesm2022/sd-angular-core.mjs.map +1 -1
- package/forms/checkbox/src/checkbox.component.d.ts +3 -3
- package/forms/chip/src/chip.component.d.ts +3 -2
- package/forms/chip-calendar/src/chip-calendar.component.d.ts +3 -2
- package/forms/date/src/date.component.d.ts +2 -3
- package/forms/date-range/src/date-range.component.d.ts +2 -3
- package/forms/datetime/src/datetime.component.d.ts +1 -0
- package/forms/datetime/src/popup/sd-datetime-picker.component.d.ts +10 -11
- package/forms/radio/src/radio.component.d.ts +3 -3
- package/forms/switch/src/switch.component.d.ts +3 -3
- package/i18n/index.d.ts +5 -5
- package/i18n/src/en.d.ts +400 -2
- package/i18n/src/i18n.messages.d.ts +2 -0
- package/i18n/src/i18n.pipe.d.ts +9 -0
- package/i18n/src/i18n.service.d.ts +14 -0
- package/i18n/src/i18n.token.d.ts +1 -0
- package/i18n/src/i18n.types.d.ts +31 -0
- package/i18n/src/ja.d.ts +2 -0
- package/i18n/src/ko.d.ts +2 -0
- package/i18n/src/vi.d.ts +2 -312
- package/i18n/src/zh.d.ts +2 -0
- package/models/index.d.ts +1 -0
- package/models/src/language.model.d.ts +4 -0
- package/modules/layout/modules/home/components/home-page/home-page.component.d.ts +25 -0
- package/package.json +71 -67
- package/public-api.d.ts +0 -1
- package/sd-angular-core-19.0.0-beta.95.tgz +0 -0
- package/i18n/src/sd-i18n.messages.d.ts +0 -2
- package/i18n/src/sd-i18n.pipe.d.ts +0 -9
- package/i18n/src/sd-i18n.service.d.ts +0 -12
- package/i18n/src/sd-i18n.token.d.ts +0 -1
- package/i18n/src/sd-i18n.types.d.ts +0 -5
- package/sd-angular-core-19.0.0-beta.94.tgz +0 -0
|
@@ -1,10 +1,10 @@
|
|
|
1
|
+
import { SUPPORTED_LANGUAGES } from '@sd-angular/core/models';
|
|
2
|
+
export { SUPPORTED_LANGUAGES } from '@sd-angular/core/models';
|
|
1
3
|
import * as i0 from '@angular/core';
|
|
2
4
|
import { inject, signal, computed, Injectable, Pipe } from '@angular/core';
|
|
3
5
|
import { SD_CORE_CONFIGURATION } from '@sd-angular/core/configurations';
|
|
4
6
|
|
|
5
|
-
const
|
|
6
|
-
|
|
7
|
-
const SD_SUPPORTED_LANGUAGES = ['vi', 'en'];
|
|
7
|
+
const I18N_STORAGE_KEY = 'sd-core.language';
|
|
8
8
|
|
|
9
9
|
const EN_MESSAGES = {
|
|
10
10
|
'core.common.cancel': 'Cancel',
|
|
@@ -41,9 +41,6 @@ const EN_MESSAGES = {
|
|
|
41
41
|
'core.operator.not-in.display': 'Not in',
|
|
42
42
|
'core.operator.null.display': 'Is empty',
|
|
43
43
|
'core.operator.not-null.display': 'Is not empty',
|
|
44
|
-
// ---- Utility errors (utility.extension.ts) ----
|
|
45
|
-
'core.utility.upload.invalid-format': '[{name}] Invalid file format. Please select again',
|
|
46
|
-
'core.utility.upload.invalid-size': '[{name}] Invalid file size. Please choose a different file',
|
|
47
44
|
// ---- Global error handler ----
|
|
48
45
|
'core.handler.global-error.update-title': 'A NEW SYSTEM UPDATE IS AVAILABLE',
|
|
49
46
|
'core.handler.global-error.update-body': 'The current version is outdated and could not load resources.\nPlease press OK to reload the page.',
|
|
@@ -236,6 +233,28 @@ const EN_MESSAGES = {
|
|
|
236
233
|
'core.component.form-builder.upload-source.all': 'All',
|
|
237
234
|
'core.component.form-builder.upload-source.photo-library': 'Pick from library',
|
|
238
235
|
'core.component.form-builder.upload-source.capture': 'Take photo',
|
|
236
|
+
// Form-builder UI v2 (M3 redesign)
|
|
237
|
+
'core.component.form-builder.components': 'Components',
|
|
238
|
+
'core.component.form-builder.search-components': 'Search components…',
|
|
239
|
+
'core.component.form-builder.view-json': 'View JSON',
|
|
240
|
+
'core.component.form-builder.design': 'Design',
|
|
241
|
+
'core.component.form-builder.preview-runtime': 'Preview · Runtime',
|
|
242
|
+
'core.component.form-builder.cancel': 'Cancel',
|
|
243
|
+
'core.component.form-builder.submit': 'Submit',
|
|
244
|
+
'core.component.form-builder.empty-title': 'Drag components here to start',
|
|
245
|
+
'core.component.form-builder.empty-hint': 'Build your form by dragging fields from the left panel, or press',
|
|
246
|
+
'core.component.form-builder.conditional': 'Conditional',
|
|
247
|
+
'core.component.form-builder.group-drop-here': 'Drop a field here to add it to this group',
|
|
248
|
+
'core.component.form-builder.hidden': 'Hidden',
|
|
249
|
+
'core.component.form-builder.read-only': 'Read only',
|
|
250
|
+
'core.component.form-builder.untitled': 'Untitled',
|
|
251
|
+
'core.component.form-builder.no-selection-title': 'Nothing selected',
|
|
252
|
+
'core.component.form-builder.no-selection-hint': 'Select a component on the canvas to edit its attributes.',
|
|
253
|
+
'core.component.form-builder.group-children': 'Children',
|
|
254
|
+
'core.component.form-builder.group-icon': 'Icon',
|
|
255
|
+
'core.component.form-builder.group-accent-color': 'Accent color',
|
|
256
|
+
'core.component.form-builder.group-no-children': 'No fields yet. Add or drag fields into this group.',
|
|
257
|
+
'core.component.form-builder.break': 'Break',
|
|
239
258
|
// ---- Component: code-editor ----
|
|
240
259
|
'core.component.code-editor.copied': 'Copied!',
|
|
241
260
|
'core.component.code-editor.copy': 'Copy code',
|
|
@@ -274,6 +293,71 @@ const EN_MESSAGES = {
|
|
|
274
293
|
// ---- Component: preview-image ----
|
|
275
294
|
'core.component.preview-image.no-image': 'No image information',
|
|
276
295
|
'core.component.preview-image.title': 'Preview image',
|
|
296
|
+
'core.component.preview-image.no-image-hint': 'There are no images to display',
|
|
297
|
+
'core.component.preview-image.load-error': 'Failed to load image',
|
|
298
|
+
'core.component.preview-image.load-error-hint': 'The image may have been deleted or the path is invalid',
|
|
299
|
+
'core.component.preview-image.retry': 'Retry',
|
|
300
|
+
'core.component.preview-image.close': 'Close',
|
|
301
|
+
'core.component.preview-image.prev': 'Previous image',
|
|
302
|
+
'core.component.preview-image.next': 'Next image',
|
|
303
|
+
'core.component.preview-image.zoom-in': 'Zoom in',
|
|
304
|
+
'core.component.preview-image.zoom-out': 'Zoom out',
|
|
305
|
+
'core.component.preview-image.fit': 'Fit to screen',
|
|
306
|
+
'core.component.preview-image.rotate': 'Rotate',
|
|
307
|
+
'core.component.preview-image.download': 'Download',
|
|
308
|
+
'core.component.preview-image.fullscreen': 'Fullscreen',
|
|
309
|
+
'core.component.preview-image.loading': 'Loading image...',
|
|
310
|
+
'core.component.preview-image.kbd-hint-nav': 'navigate',
|
|
311
|
+
'core.component.preview-image.kbd-hint-close': 'close',
|
|
312
|
+
// ---- Component: preview-pdf ----
|
|
313
|
+
'core.component.preview-pdf.title': 'Preview document',
|
|
314
|
+
'core.component.preview-pdf.close': 'Close',
|
|
315
|
+
'core.component.preview-pdf.pages-count': '{count} pages',
|
|
316
|
+
'core.component.preview-pdf.tab.thumbnails': 'Pages',
|
|
317
|
+
'core.component.preview-pdf.tab.outline': 'Outline',
|
|
318
|
+
'core.component.preview-pdf.tab.search': 'Find',
|
|
319
|
+
'core.component.preview-pdf.first-page': 'First page',
|
|
320
|
+
'core.component.preview-pdf.prev-page': 'Previous page',
|
|
321
|
+
'core.component.preview-pdf.next-page': 'Next page',
|
|
322
|
+
'core.component.preview-pdf.last-page': 'Last page',
|
|
323
|
+
'core.component.preview-pdf.zoom-in': 'Zoom in',
|
|
324
|
+
'core.component.preview-pdf.zoom-out': 'Zoom out',
|
|
325
|
+
'core.component.preview-pdf.fit-page': 'Fit page',
|
|
326
|
+
'core.component.preview-pdf.fit-width': 'Fit width',
|
|
327
|
+
'core.component.preview-pdf.actual-size': 'Actual size',
|
|
328
|
+
'core.component.preview-pdf.rotate': 'Rotate',
|
|
329
|
+
'core.component.preview-pdf.scroll-page': 'Single page',
|
|
330
|
+
'core.component.preview-pdf.scroll-continuous': 'Continuous scroll',
|
|
331
|
+
'core.component.preview-pdf.print': 'Print',
|
|
332
|
+
'core.component.preview-pdf.download': 'Download',
|
|
333
|
+
'core.component.preview-pdf.fullscreen': 'Fullscreen',
|
|
334
|
+
'core.component.preview-pdf.toggle-sidebar': 'Toggle sidebar',
|
|
335
|
+
'core.component.preview-pdf.page-of': 'page {current} / {total}',
|
|
336
|
+
'core.component.preview-pdf.empty.title': 'No document',
|
|
337
|
+
'core.component.preview-pdf.empty.subtitle': 'No PDF file to display yet',
|
|
338
|
+
'core.component.preview-pdf.loading': 'Loading document...',
|
|
339
|
+
'core.component.preview-pdf.loading.page': 'Processing page {current} / {total}',
|
|
340
|
+
'core.component.preview-pdf.error.invalid.title': 'Failed to load document',
|
|
341
|
+
'core.component.preview-pdf.error.invalid.body': 'The PDF file may be corrupted. Please check the file.',
|
|
342
|
+
'core.component.preview-pdf.error.password.title': 'Document is protected',
|
|
343
|
+
'core.component.preview-pdf.error.password.body': 'This PDF file requires a password to open.',
|
|
344
|
+
'core.component.preview-pdf.error.network.title': 'Cannot connect',
|
|
345
|
+
'core.component.preview-pdf.error.network.body': 'Unable to load the file from the server. Please try again later.',
|
|
346
|
+
'core.component.preview-pdf.error.unknown.title': 'An error occurred',
|
|
347
|
+
'core.component.preview-pdf.error.unknown.body': 'Please retry or download the original file to view it.',
|
|
348
|
+
'core.component.preview-pdf.error.retry': 'Retry',
|
|
349
|
+
'core.component.preview-pdf.error.download-raw': 'Download original',
|
|
350
|
+
'core.component.preview-pdf.deferred.outline': 'Outline will be added in a future version.',
|
|
351
|
+
'core.component.preview-pdf.deferred.search': 'Search will be added in a future version.',
|
|
352
|
+
'core.component.preview-pdf.search': 'Search',
|
|
353
|
+
'core.component.preview-pdf.search-placeholder': 'Search in document...',
|
|
354
|
+
'core.component.preview-pdf.search-case': 'Match case',
|
|
355
|
+
'core.component.preview-pdf.search-whole': 'Whole word',
|
|
356
|
+
'core.component.preview-pdf.search-no-results': 'No results',
|
|
357
|
+
'core.component.preview-pdf.search-results-count': '{count} results for "{term}"',
|
|
358
|
+
'core.component.preview-pdf.search-prev': 'Previous match',
|
|
359
|
+
'core.component.preview-pdf.search-next': 'Next match',
|
|
360
|
+
'core.component.preview-pdf.search-close': 'Close search',
|
|
277
361
|
// ---- Component: table ----
|
|
278
362
|
'core.component.table.setup': 'Table setup',
|
|
279
363
|
'core.component.table.column-header': 'Column header',
|
|
@@ -349,12 +433,896 @@ const EN_MESSAGES = {
|
|
|
349
433
|
'core.module.layout.not-found.back': 'Go back',
|
|
350
434
|
// ---- Module: layout (home page) ----
|
|
351
435
|
'core.module.layout.home.tab-name': 'Home',
|
|
352
|
-
'core.module.layout.home.
|
|
353
|
-
'core.module.layout.home.
|
|
436
|
+
'core.module.layout.home.feature.data': 'Data',
|
|
437
|
+
'core.module.layout.home.feature.reports': 'Reports',
|
|
438
|
+
'core.module.layout.home.feature.users': 'Users',
|
|
439
|
+
'core.module.layout.home.feature.workflow': 'Workflow',
|
|
440
|
+
'core.module.layout.home.feature.audit': 'Audit',
|
|
441
|
+
'core.module.layout.home.feature.integration': 'Integration',
|
|
442
|
+
// ---- Module: layout (mock fallback when SD_LAYOUT_CONFIGURATION is not provided) ----
|
|
443
|
+
'core.module.layout.mock.user.full-name': 'Demo User',
|
|
354
444
|
// ---- Module: generic (generic-select) ----
|
|
355
445
|
'core.module.generic.generic-select.detail-link': 'details',
|
|
356
446
|
};
|
|
357
447
|
|
|
448
|
+
const JA_MESSAGES = {
|
|
449
|
+
'core.common.cancel': 'キャンセル',
|
|
450
|
+
'core.common.close': '閉じる',
|
|
451
|
+
'core.common.reload': 'ページを再読み込み',
|
|
452
|
+
'core.test.greet': 'こんにちは {name}さん',
|
|
453
|
+
// ---- Validators (pattern.model.ts) ----
|
|
454
|
+
'core.validator.email.name': 'メールアドレス',
|
|
455
|
+
'core.validator.email.error': 'メールアドレスの形式が正しくありません',
|
|
456
|
+
'core.validator.phone.name': '電話番号',
|
|
457
|
+
'core.validator.phone.error': '電話番号の形式が正しくありません',
|
|
458
|
+
'core.validator.phone-vn.name': 'VN電話番号',
|
|
459
|
+
'core.validator.phone-vn.error': '電話番号の形式が正しくありません',
|
|
460
|
+
'core.validator.cccd.name': '個人番号',
|
|
461
|
+
'core.validator.cccd.error': '個人番号の形式が正しくありません(12桁)',
|
|
462
|
+
'core.validator.passport.name': 'パスポート',
|
|
463
|
+
'core.validator.passport.error': 'パスポート番号の形式が正しくありません(英字1文字 + 数字7桁)',
|
|
464
|
+
'core.validator.id-vn.name': '個人番号 / パスポート',
|
|
465
|
+
'core.validator.id-vn.error': '個人番号またはパスポート番号の形式が正しくありません',
|
|
466
|
+
'core.validator.time.name': '時刻',
|
|
467
|
+
'core.validator.time.error': '時刻の形式が正しくありません(HH:mm 形式)',
|
|
468
|
+
// ---- Operators (operator.model.ts) ----
|
|
469
|
+
'core.operator.equal.display': '等しい',
|
|
470
|
+
'core.operator.not-equal.display': '等しくない',
|
|
471
|
+
'core.operator.greater-than.display': 'より大きい',
|
|
472
|
+
'core.operator.less-than.display': 'より小さい',
|
|
473
|
+
'core.operator.greater-or-equal.display': '以上',
|
|
474
|
+
'core.operator.less-or-equal.display': '以下',
|
|
475
|
+
'core.operator.contain.display': '含む',
|
|
476
|
+
'core.operator.not-contain.display': '含まない',
|
|
477
|
+
'core.operator.start-with.display': 'で始まる',
|
|
478
|
+
'core.operator.end-with.display': 'で終わる',
|
|
479
|
+
'core.operator.in.display': 'いずれかに一致',
|
|
480
|
+
'core.operator.not-in.display': 'いずれにも一致しない',
|
|
481
|
+
'core.operator.null.display': '空である',
|
|
482
|
+
'core.operator.not-null.display': '空でない',
|
|
483
|
+
// ---- Global error handler ----
|
|
484
|
+
'core.handler.global-error.update-title': '新しいシステムアップデートがあります',
|
|
485
|
+
'core.handler.global-error.update-body': '現在のバージョンが古いため、リソースを読み込めませんでした。\nOKを押してページを再読み込みしてください。',
|
|
486
|
+
// ---- Interceptor: no-internet ----
|
|
487
|
+
'core.interceptor.no-internet.offline': 'ネットワーク接続がありません。接続を待機中...',
|
|
488
|
+
'core.interceptor.no-internet.cors-error': 'サーバーに接続できません(CORSまたは設定エラー)。',
|
|
489
|
+
'core.interceptor.no-internet.maintenance': 'サーバーはメンテナンス中です。しばらくしてから再度お試しください。',
|
|
490
|
+
'core.interceptor.no-internet.restored': '接続が復旧しました。',
|
|
491
|
+
// ---- Service: excel ----
|
|
492
|
+
'core.excel.cannot-read-file': 'ファイルの内容を読み取れませんでした',
|
|
493
|
+
'core.excel.no-sheet': 'Excelファイルにデータシートがありません',
|
|
494
|
+
// ---- Service: docx ----
|
|
495
|
+
'core.docx.invalid-format': '形式が正しくありません。DOCまたはDOCX形式のテンプレートを選択してください',
|
|
496
|
+
'core.docx.size-exceeded': 'テンプレートファイルのサイズが上限を超えています。もう一度お試しください',
|
|
497
|
+
'core.docx.convert-error': 'DOCXファイルの変換中にエラーが発生しました',
|
|
498
|
+
// ---- Service: confirm ----
|
|
499
|
+
'core.confirm.title': '確認',
|
|
500
|
+
'core.confirm.yes': 'OK',
|
|
501
|
+
'core.confirm.no': 'キャンセル',
|
|
502
|
+
'core.confirm.yes-short': 'はい',
|
|
503
|
+
'core.confirm.no-short': 'いいえ',
|
|
504
|
+
// ---- Directive: hover-copy ----
|
|
505
|
+
'core.directive.hover-copy.tooltip': 'コピー',
|
|
506
|
+
// ---- Forms: input ----
|
|
507
|
+
'core.form.input.required': '入力してください',
|
|
508
|
+
'core.form.input.maxlength': '最大文字数: {max}',
|
|
509
|
+
'core.form.input.invalid-pattern': '形式が正しくありません',
|
|
510
|
+
'core.form.input.exceeded': '最大文字数を超えています',
|
|
511
|
+
// ---- Forms: autocomplete ----
|
|
512
|
+
'core.form.autocomplete.required': '入力してください',
|
|
513
|
+
// ---- Forms: chip ----
|
|
514
|
+
'core.form.chip.required': '入力してください',
|
|
515
|
+
'core.form.chip.minlength': '{min}件以上入力してください',
|
|
516
|
+
'core.form.chip.maxlength': '{max}件以内で入力してください',
|
|
517
|
+
// ---- Forms: chip-calendar ----
|
|
518
|
+
'core.form.chip-calendar.required': '入力してください',
|
|
519
|
+
'core.form.chip-calendar.minlength': '{min}件以上入力してください',
|
|
520
|
+
'core.form.chip-calendar.maxlength': '{max}件以内で入力してください',
|
|
521
|
+
// ---- Forms: date ----
|
|
522
|
+
'core.form.date.required': '入力してください',
|
|
523
|
+
'core.form.date.min-date': '最小日付: {date}',
|
|
524
|
+
'core.form.date.max-date': '最大日付: {date}',
|
|
525
|
+
'core.form.date.parse-error': '解析エラー: {text}',
|
|
526
|
+
'core.form.date.invalid-format': '形式が正しくありません',
|
|
527
|
+
// ---- Forms: date-range ----
|
|
528
|
+
'core.form.date-range.required': '入力してください',
|
|
529
|
+
'core.form.date-range.invalid-min': '開始日が無効です(下限を下回っています)',
|
|
530
|
+
'core.form.date-range.invalid-max': '終了日が無効です(上限を超えています)',
|
|
531
|
+
'core.form.date-range.from': '開始',
|
|
532
|
+
'core.form.date-range.to': '~',
|
|
533
|
+
// ---- Forms: datetime ----
|
|
534
|
+
'core.form.datetime.required': '入力してください',
|
|
535
|
+
'core.form.datetime.min-date': '最小日付: {date}',
|
|
536
|
+
'core.form.datetime.max-date': '最大日付: {date}',
|
|
537
|
+
'core.form.datetime.invalid-format': '形式が正しくありません',
|
|
538
|
+
'core.form.datetime.now': '現在',
|
|
539
|
+
'core.form.datetime.confirm': '確定',
|
|
540
|
+
// ---- Forms: time-spinner ----
|
|
541
|
+
'core.form.time-spinner.hour': '時',
|
|
542
|
+
'core.form.time-spinner.minute': '分',
|
|
543
|
+
'core.form.time-spinner.second': '秒',
|
|
544
|
+
'core.form.time-spinner.increase-hour': '時を増やす',
|
|
545
|
+
'core.form.time-spinner.decrease-hour': '時を減らす',
|
|
546
|
+
'core.form.time-spinner.increase-minute': '分を増やす',
|
|
547
|
+
'core.form.time-spinner.decrease-minute': '分を減らす',
|
|
548
|
+
'core.form.time-spinner.increase-second': '秒を増やす',
|
|
549
|
+
'core.form.time-spinner.decrease-second': '秒を減らす',
|
|
550
|
+
// ---- Forms: input-number ----
|
|
551
|
+
'core.form.input-number.required': '入力してください',
|
|
552
|
+
'core.form.input-number.min': '{min}以上の値を入力してください',
|
|
553
|
+
'core.form.input-number.max': '{max}以下の値を入力してください',
|
|
554
|
+
// ---- Forms: radio ----
|
|
555
|
+
'core.form.radio.required': '選択してください',
|
|
556
|
+
// ---- Forms: select ----
|
|
557
|
+
'core.form.select.required': '選択してください',
|
|
558
|
+
// ---- Forms: textarea ----
|
|
559
|
+
'core.form.textarea.required': '入力してください',
|
|
560
|
+
'core.form.textarea.maxlength': '最大文字数: {max}',
|
|
561
|
+
'core.form.textarea.invalid-pattern': '形式が正しくありません',
|
|
562
|
+
'core.form.textarea.exceeded': '最大文字数を超えています',
|
|
563
|
+
// ---- Component: editor ----
|
|
564
|
+
'core.component.editor.required': '内容を入力してください',
|
|
565
|
+
'core.component.editor.maxlength': '最大文字数: {max}',
|
|
566
|
+
'core.component.editor.image.invalid-format': 'ファイル形式 ".{format}" は許可されていません。許可される形式: {allowed}',
|
|
567
|
+
'core.component.editor.image.size-exceeded': 'ファイルサイズ {sizeMB}MB は上限の {maxSizeMB}MB を超えています',
|
|
568
|
+
'core.component.editor.image.min-width': '画像の幅 {width}px は最小値 {min}px を下回っています',
|
|
569
|
+
'core.component.editor.image.min-height': '画像の高さ {height}px は最小値 {min}px を下回っています',
|
|
570
|
+
'core.component.editor.image.max-width': '画像の幅 {width}px は上限 {max}px を超えています',
|
|
571
|
+
'core.component.editor.image.max-height': '画像の高さ {height}px は上限 {max}px を超えています',
|
|
572
|
+
'core.component.editor.image.max-per-selection': '一度に選択できる画像は最大{max}枚です',
|
|
573
|
+
// ---- Component: document-builder ----
|
|
574
|
+
'core.component.document-builder.page-number.current': '現在のページ番号',
|
|
575
|
+
'core.component.document-builder.page-number.total': '総ページ数',
|
|
576
|
+
'core.component.document-builder.ck-comment.label': 'コメント',
|
|
577
|
+
'core.component.document-builder.ck-comment.text-too-long': 'テキストが長すぎます({length}文字)。最大{max}文字です。',
|
|
578
|
+
'core.component.document-builder.variable.not-allowed': 'テキストへの変数の追加は許可されていません',
|
|
579
|
+
'core.component.document-builder.variable.invalid-data': '変数データが正しくありません',
|
|
580
|
+
// ---- Component: form-builder ----
|
|
581
|
+
'core.component.form-builder.field-key': 'フィールドキー',
|
|
582
|
+
'core.component.form-builder.display': '表示',
|
|
583
|
+
'core.component.form-builder.general': '一般',
|
|
584
|
+
'core.component.form-builder.visible-when': '表示条件',
|
|
585
|
+
'core.component.form-builder.required': '必須',
|
|
586
|
+
'core.component.form-builder.label': 'ラベル',
|
|
587
|
+
'core.component.form-builder.disabled': '無効',
|
|
588
|
+
'core.component.form-builder.disabled-when': '無効化条件',
|
|
589
|
+
'core.component.form-builder.hidden-when': '非表示条件',
|
|
590
|
+
'core.component.form-builder.validation': 'バリデーション',
|
|
591
|
+
'core.component.form-builder.required-when': '必須条件',
|
|
592
|
+
'core.component.form-builder.confirm': '確認',
|
|
593
|
+
'core.component.form-builder.delete': '削除',
|
|
594
|
+
'core.component.form-builder.save': '保存',
|
|
595
|
+
'core.component.form-builder.hint': 'ヒント',
|
|
596
|
+
'core.component.form-builder.parameter': 'パラメータ',
|
|
597
|
+
'core.component.form-builder.add-field': 'フィールドを追加',
|
|
598
|
+
'core.component.form-builder.data': 'データ',
|
|
599
|
+
'core.component.form-builder.query-condition': 'クエリ条件',
|
|
600
|
+
'core.component.form-builder.set-query-value': 'クエリ値を設定',
|
|
601
|
+
'core.component.form-builder.value-source-field': 'ソースフィールド',
|
|
602
|
+
'core.component.form-builder.assign-parameter': 'パラメータを割り当て',
|
|
603
|
+
'core.component.form-builder.template-data': 'テンプレートデータ',
|
|
604
|
+
'core.component.form-builder.set-expression': '式を設定',
|
|
605
|
+
'core.component.form-builder.condition-group': '条件グループ',
|
|
606
|
+
'core.component.form-builder.condition': '条件',
|
|
607
|
+
'core.component.form-builder.layout': 'レイアウト',
|
|
608
|
+
'core.component.form-builder.maxlength': '最大文字数',
|
|
609
|
+
'core.component.form-builder.assign-parameter-value': 'パラメータ値を割り当て',
|
|
610
|
+
'core.component.form-builder.parameter-name': 'パラメータ名',
|
|
611
|
+
'core.component.form-builder.parameter-value': 'パラメータ値',
|
|
612
|
+
'core.component.form-builder.assign-value': '値を割り当て',
|
|
613
|
+
'core.component.form-builder.add-data': 'データを追加',
|
|
614
|
+
'core.component.form-builder.data-api': 'APIデータ',
|
|
615
|
+
'core.component.form-builder.data-static': '静的データ',
|
|
616
|
+
'core.component.form-builder.set-on-change-assign': '変更時の割り当てを設定',
|
|
617
|
+
'core.component.form-builder.target-field': '対象フィールド',
|
|
618
|
+
'core.component.form-builder.target-value': '対象値',
|
|
619
|
+
'core.component.form-builder.column-data': '列データ',
|
|
620
|
+
'core.component.form-builder.add-column': '列を追加',
|
|
621
|
+
'core.component.form-builder.column-config': '列設定',
|
|
622
|
+
'core.component.form-builder.column-name': '列名',
|
|
623
|
+
'core.component.form-builder.width': '幅',
|
|
624
|
+
'core.component.form-builder.data-type': 'データ型',
|
|
625
|
+
'core.component.form-builder.show-when-true': 'TRUEのとき表示',
|
|
626
|
+
'core.component.form-builder.show-when-false': 'FALSEのとき表示',
|
|
627
|
+
'core.component.form-builder.column-list': '列一覧',
|
|
628
|
+
'core.component.form-builder.yes-no': 'はい/いいえ',
|
|
629
|
+
'core.component.form-builder.config-validation-error-warning': 'エラー/警告のバリデーションを設定',
|
|
630
|
+
'core.component.form-builder.message-type': 'メッセージ種別',
|
|
631
|
+
'core.component.form-builder.message-display': '表示メッセージ',
|
|
632
|
+
'core.component.form-builder.condition-expression': '条件式',
|
|
633
|
+
'core.component.form-builder.add-validation': 'バリデーションを追加',
|
|
634
|
+
'core.component.form-builder.expression': '式',
|
|
635
|
+
'core.component.form-builder.available-methods': '利用可能なメソッド',
|
|
636
|
+
'core.component.form-builder.format': 'フォーマット',
|
|
637
|
+
'core.component.form-builder.time': '時刻',
|
|
638
|
+
'core.component.form-builder.content': '内容',
|
|
639
|
+
'core.component.form-builder.min': '最小',
|
|
640
|
+
'core.component.form-builder.max': '最大',
|
|
641
|
+
'core.component.form-builder.vertical': '縦',
|
|
642
|
+
'core.component.form-builder.multiple': '複数選択',
|
|
643
|
+
'core.component.form-builder.default-value': 'デフォルト値',
|
|
644
|
+
'core.component.form-builder.type': '種別',
|
|
645
|
+
'core.component.form-builder.file': 'ファイル',
|
|
646
|
+
'core.component.form-builder.image': '画像',
|
|
647
|
+
'core.component.form-builder.max-files': 'ファイル/画像の最大数',
|
|
648
|
+
'core.component.form-builder.size-mb': 'サイズ (MB)',
|
|
649
|
+
'core.component.form-builder.format-example': 'フォーマット (例: png,jpg ...)',
|
|
650
|
+
'core.component.form-builder.source-mobile': 'ソース (モバイル)',
|
|
651
|
+
'core.component.form-builder.config-variable': '変数を設定',
|
|
652
|
+
'core.component.form-builder.config-validation-warning-error': '警告/エラーのバリデーションを設定',
|
|
653
|
+
'core.component.form-builder.back-to-design': 'デザインに戻る',
|
|
654
|
+
'core.component.form-builder.preview': 'プレビュー',
|
|
655
|
+
'core.component.form-builder.drag-vertically': '上下にドラッグ',
|
|
656
|
+
'core.component.form-builder.unset-readonly': '読み取り専用を解除',
|
|
657
|
+
'core.component.form-builder.set-readonly': '読み取り専用',
|
|
658
|
+
'core.component.form-builder.duplicate': '複製',
|
|
659
|
+
'core.component.form-builder.show': '表示',
|
|
660
|
+
'core.component.form-builder.hide': '非表示',
|
|
661
|
+
'core.component.form-builder.flex': 'フレックス',
|
|
662
|
+
'core.component.form-builder.display-label': '表示ラベル',
|
|
663
|
+
'core.component.form-builder.attribute': '属性',
|
|
664
|
+
'core.component.form-builder.add-variable': '変数を追加',
|
|
665
|
+
'core.component.form-builder.add-new': '新規追加',
|
|
666
|
+
'core.component.form-builder.detail': '詳細',
|
|
667
|
+
'core.component.form-builder.create-update': '作成/更新',
|
|
668
|
+
'core.component.form-builder.default': 'デフォルト',
|
|
669
|
+
'core.component.form-builder.show-more': 'もっと見る',
|
|
670
|
+
'core.component.form-builder.show-less': '折りたたむ',
|
|
671
|
+
'core.component.form-builder.row-overflow': '合計サイズが12列を超えるため、この行に移動できません',
|
|
672
|
+
'core.component.form-builder.upload-source.all': 'すべて',
|
|
673
|
+
'core.component.form-builder.upload-source.photo-library': 'ライブラリから選択',
|
|
674
|
+
'core.component.form-builder.upload-source.capture': '写真を撮影',
|
|
675
|
+
// Form-builder UI v2 (M3 redesign)
|
|
676
|
+
'core.component.form-builder.components': 'コンポーネント',
|
|
677
|
+
'core.component.form-builder.search-components': 'コンポーネントを検索…',
|
|
678
|
+
'core.component.form-builder.view-json': 'JSONを表示',
|
|
679
|
+
'core.component.form-builder.design': 'デザイン',
|
|
680
|
+
'core.component.form-builder.preview-runtime': 'プレビュー · ランタイム',
|
|
681
|
+
'core.component.form-builder.cancel': 'キャンセル',
|
|
682
|
+
'core.component.form-builder.submit': '送信',
|
|
683
|
+
'core.component.form-builder.empty-title': 'コンポーネントをここにドラッグして開始',
|
|
684
|
+
'core.component.form-builder.empty-hint': '左パネルからフィールドをドラッグしてフォームを構築するか、次を押します:',
|
|
685
|
+
'core.component.form-builder.conditional': '条件付き',
|
|
686
|
+
'core.component.form-builder.group-drop-here': 'フィールドをここにドロップしてグループに追加',
|
|
687
|
+
'core.component.form-builder.hidden': '非表示',
|
|
688
|
+
'core.component.form-builder.read-only': '読み取り専用',
|
|
689
|
+
'core.component.form-builder.untitled': '無題',
|
|
690
|
+
'core.component.form-builder.no-selection-title': '選択なし',
|
|
691
|
+
'core.component.form-builder.no-selection-hint': 'キャンバスでコンポーネントを選択して属性を編集します。',
|
|
692
|
+
'core.component.form-builder.group-children': '子要素',
|
|
693
|
+
'core.component.form-builder.group-icon': 'アイコン',
|
|
694
|
+
'core.component.form-builder.group-accent-color': 'アクセントカラー',
|
|
695
|
+
'core.component.form-builder.group-no-children': 'フィールドがまだありません。このグループにフィールドを追加またはドラッグしてください。',
|
|
696
|
+
'core.component.form-builder.break': '改行',
|
|
697
|
+
// ---- Component: code-editor ----
|
|
698
|
+
'core.component.code-editor.copied': 'コピーしました!',
|
|
699
|
+
'core.component.code-editor.copy': 'コードをコピー',
|
|
700
|
+
// ---- Component: history ----
|
|
701
|
+
'core.component.history.by': '実行者',
|
|
702
|
+
// ---- Component: import-excel ----
|
|
703
|
+
'core.component.import-excel.title': 'Excelデータをインポート',
|
|
704
|
+
'core.component.import-excel.see-all': 'すべて表示',
|
|
705
|
+
'core.component.import-excel.valid-rows': '有効な行数',
|
|
706
|
+
'core.component.import-excel.error-rows': 'エラー行数',
|
|
707
|
+
'core.component.import-excel.warning-rows': '警告行数',
|
|
708
|
+
'core.component.import-excel.valid-data': '有効なデータ',
|
|
709
|
+
'core.component.import-excel.download-template-tooltip': 'クリックしてテンプレートをダウンロード',
|
|
710
|
+
'core.component.import-excel.upload': 'アップロード',
|
|
711
|
+
'core.component.import-excel.download': 'ダウンロード',
|
|
712
|
+
'core.component.import-excel.confirm-save': '確認して保存',
|
|
713
|
+
'core.component.import-excel.status': 'ステータス',
|
|
714
|
+
'core.component.import-excel.no-data-upload': 'アップロードデータがありません',
|
|
715
|
+
'core.component.import-excel.click-here-template': 'ここをクリックしてテンプレートをダウンロード',
|
|
716
|
+
'core.component.import-excel.no-data-in-file': 'ファイルにデータがありません',
|
|
717
|
+
'core.component.import-excel.row-limit': 'アップロード上限は{limit}行です',
|
|
718
|
+
'core.component.import-excel.required': '必須データ',
|
|
719
|
+
'core.component.import-excel.min-length': '最小文字数: {min}',
|
|
720
|
+
'core.component.import-excel.max-length': '最大文字数: {max}',
|
|
721
|
+
'core.component.import-excel.not-a-number': '{value} は有効な数値ではありません',
|
|
722
|
+
'core.component.import-excel.below-min': '{value} は最小値 {min} を下回っています',
|
|
723
|
+
'core.component.import-excel.above-max': '{value} は最大値 {max} を超えています',
|
|
724
|
+
'core.component.import-excel.invalid-bool': '有効な値を入力してください (true, false, 1, 0)',
|
|
725
|
+
'core.component.import-excel.invalid-value': '値 {value} は正しくありません',
|
|
726
|
+
'core.component.import-excel.value-not-in-list': '値 {value} は許可されたリスト [{list}] に含まれていません',
|
|
727
|
+
'core.component.import-excel.invalid-date-format': '日付 {value} はフォーマット {format} と一致しません',
|
|
728
|
+
'core.component.import-excel.generic-error': 'エラーが発生しました',
|
|
729
|
+
'core.component.import-excel.notify-title': 'お知らせ',
|
|
730
|
+
'core.component.import-excel.message-column': 'メッセージ',
|
|
731
|
+
'core.component.import-excel.success': '成功',
|
|
732
|
+
// ---- Component: preview-image ----
|
|
733
|
+
'core.component.preview-image.no-image': '画像情報がありません',
|
|
734
|
+
'core.component.preview-image.title': '画像プレビュー',
|
|
735
|
+
'core.component.preview-image.no-image-hint': '表示する画像がありません',
|
|
736
|
+
'core.component.preview-image.load-error': '画像を読み込めませんでした',
|
|
737
|
+
'core.component.preview-image.load-error-hint': '画像ファイルが削除されたか、パスが無効である可能性があります',
|
|
738
|
+
'core.component.preview-image.retry': '再試行',
|
|
739
|
+
'core.component.preview-image.close': '閉じる',
|
|
740
|
+
'core.component.preview-image.prev': '前の画像',
|
|
741
|
+
'core.component.preview-image.next': '次の画像',
|
|
742
|
+
'core.component.preview-image.zoom-in': '拡大',
|
|
743
|
+
'core.component.preview-image.zoom-out': '縮小',
|
|
744
|
+
'core.component.preview-image.fit': '画面に合わせる',
|
|
745
|
+
'core.component.preview-image.rotate': '回転',
|
|
746
|
+
'core.component.preview-image.download': 'ダウンロード',
|
|
747
|
+
'core.component.preview-image.fullscreen': '全画面表示',
|
|
748
|
+
'core.component.preview-image.loading': '画像を読み込み中...',
|
|
749
|
+
'core.component.preview-image.kbd-hint-nav': '画像切替',
|
|
750
|
+
'core.component.preview-image.kbd-hint-close': '閉じる',
|
|
751
|
+
// ---- Component: preview-pdf ----
|
|
752
|
+
'core.component.preview-pdf.title': 'ドキュメントを表示',
|
|
753
|
+
'core.component.preview-pdf.close': '閉じる',
|
|
754
|
+
'core.component.preview-pdf.pages-count': '{count} ページ',
|
|
755
|
+
'core.component.preview-pdf.tab.thumbnails': 'ページ',
|
|
756
|
+
'core.component.preview-pdf.tab.outline': '目次',
|
|
757
|
+
'core.component.preview-pdf.tab.search': '検索',
|
|
758
|
+
'core.component.preview-pdf.first-page': '最初のページ',
|
|
759
|
+
'core.component.preview-pdf.prev-page': '前のページ',
|
|
760
|
+
'core.component.preview-pdf.next-page': '次のページ',
|
|
761
|
+
'core.component.preview-pdf.last-page': '最後のページ',
|
|
762
|
+
'core.component.preview-pdf.zoom-in': '拡大',
|
|
763
|
+
'core.component.preview-pdf.zoom-out': '縮小',
|
|
764
|
+
'core.component.preview-pdf.fit-page': 'ページに合わせる',
|
|
765
|
+
'core.component.preview-pdf.fit-width': '幅に合わせる',
|
|
766
|
+
'core.component.preview-pdf.actual-size': '実際のサイズ',
|
|
767
|
+
'core.component.preview-pdf.rotate': '回転',
|
|
768
|
+
'core.component.preview-pdf.scroll-page': '単ページ',
|
|
769
|
+
'core.component.preview-pdf.scroll-continuous': '連続スクロール',
|
|
770
|
+
'core.component.preview-pdf.print': '印刷',
|
|
771
|
+
'core.component.preview-pdf.download': 'ダウンロード',
|
|
772
|
+
'core.component.preview-pdf.fullscreen': '全画面',
|
|
773
|
+
'core.component.preview-pdf.toggle-sidebar': 'サイドバー表示切替',
|
|
774
|
+
'core.component.preview-pdf.page-of': '{current} / {total} ページ',
|
|
775
|
+
'core.component.preview-pdf.empty.title': 'ドキュメントがありません',
|
|
776
|
+
'core.component.preview-pdf.empty.subtitle': '表示する PDF ファイルがまだありません',
|
|
777
|
+
'core.component.preview-pdf.loading': 'ドキュメントを読み込み中...',
|
|
778
|
+
'core.component.preview-pdf.loading.page': 'ページ {current} / {total} を処理中',
|
|
779
|
+
'core.component.preview-pdf.error.invalid.title': 'ドキュメントを読み込めません',
|
|
780
|
+
'core.component.preview-pdf.error.invalid.body': 'PDF ファイルが破損している可能性があります。ファイルを確認してください。',
|
|
781
|
+
'core.component.preview-pdf.error.password.title': '保護されたドキュメント',
|
|
782
|
+
'core.component.preview-pdf.error.password.body': 'この PDF ファイルを開くにはパスワードが必要です。',
|
|
783
|
+
'core.component.preview-pdf.error.network.title': '接続できません',
|
|
784
|
+
'core.component.preview-pdf.error.network.body': 'サーバーからファイルを読み込めません。後でもう一度お試しください。',
|
|
785
|
+
'core.component.preview-pdf.error.unknown.title': 'エラーが発生しました',
|
|
786
|
+
'core.component.preview-pdf.error.unknown.body': 'もう一度試すか、元のファイルをダウンロードしてご覧ください。',
|
|
787
|
+
'core.component.preview-pdf.error.retry': '再試行',
|
|
788
|
+
'core.component.preview-pdf.error.download-raw': '元のファイルをダウンロード',
|
|
789
|
+
'core.component.preview-pdf.deferred.outline': '目次は今後のバージョンで追加されます。',
|
|
790
|
+
'core.component.preview-pdf.deferred.search': '検索機能は今後のバージョンで追加されます。',
|
|
791
|
+
'core.component.preview-pdf.search': '検索',
|
|
792
|
+
'core.component.preview-pdf.search-placeholder': 'ドキュメント内を検索...',
|
|
793
|
+
'core.component.preview-pdf.search-case': '大文字小文字を区別',
|
|
794
|
+
'core.component.preview-pdf.search-whole': '単語単位で一致',
|
|
795
|
+
'core.component.preview-pdf.search-no-results': '見つかりません',
|
|
796
|
+
'core.component.preview-pdf.search-results-count': '「{term}」の検索結果 {count} 件',
|
|
797
|
+
'core.component.preview-pdf.search-prev': '前の結果',
|
|
798
|
+
'core.component.preview-pdf.search-next': '次の結果',
|
|
799
|
+
'core.component.preview-pdf.search-close': '検索を閉じる',
|
|
800
|
+
// ---- Component: table ----
|
|
801
|
+
'core.component.table.setup': 'テーブル設定',
|
|
802
|
+
'core.component.table.column-header': '列ヘッダー',
|
|
803
|
+
'core.component.table.width': '幅',
|
|
804
|
+
'core.component.table.fixed': '固定',
|
|
805
|
+
'core.component.table.char-limit': '文字数制限',
|
|
806
|
+
'core.component.table.skip': 'スキップ',
|
|
807
|
+
'core.component.table.apply': '適用',
|
|
808
|
+
'core.component.table.filter': 'フィルター',
|
|
809
|
+
'core.component.table.clear-selection': '選択を解除',
|
|
810
|
+
'core.component.table.customize': 'カスタマイズ',
|
|
811
|
+
'core.component.table.search': '検索',
|
|
812
|
+
'core.component.table.reload': '再読み込み',
|
|
813
|
+
'core.component.table.setup-short': '設定',
|
|
814
|
+
'core.component.table.no-results': '一致する結果がありません',
|
|
815
|
+
'core.component.table.no-results-hint': '別の条件で検索またはフィルターしてください',
|
|
816
|
+
'core.component.table.choose-filter-hint': 'まずフィルターを選択してください',
|
|
817
|
+
'core.component.table.no-data': 'データがありません',
|
|
818
|
+
'core.component.table.export-excel': 'Excelエクスポート',
|
|
819
|
+
'core.component.table.export-csv': 'CSVエクスポート',
|
|
820
|
+
'core.component.table.showing': '表示中:',
|
|
821
|
+
'core.component.table.paginator.first-page': '最初のページ',
|
|
822
|
+
'core.component.table.paginator.last-page': '最後のページ',
|
|
823
|
+
'core.component.table.paginator.items-per-page': '表示中',
|
|
824
|
+
'core.component.table.paginator.next-page': '次のページ',
|
|
825
|
+
'core.component.table.paginator.previous-page': '前のページ',
|
|
826
|
+
'core.component.table.error-occurred': 'エラーが発生しました',
|
|
827
|
+
'core.component.table.not-an-array': 'データが配列ではありません',
|
|
828
|
+
'core.component.table.config.confirm-reset': 'すべての設定をデフォルトに戻しますか',
|
|
829
|
+
'core.component.table.popup-export.select-columns': 'エクスポートする列を選択してください',
|
|
830
|
+
'core.component.table.selector-action.default-msg': '件選択中',
|
|
831
|
+
'core.component.tab-router.too-many-tabs': 'タブを開きすぎています。',
|
|
832
|
+
// ---- Component: upload-file ----
|
|
833
|
+
'core.component.upload-file.upload': 'ファイルをアップロード',
|
|
834
|
+
'core.component.upload-file.error-occurred': 'エラーが発生しました',
|
|
835
|
+
'core.component.upload-file.please-upload': 'ファイル/画像をアップロードしてください',
|
|
836
|
+
'core.component.upload-file.desc-format-and-size': 'フォーマット: {exts}、最大: {maxSize}MB',
|
|
837
|
+
'core.component.upload-file.desc-format': 'フォーマット: {exts}',
|
|
838
|
+
'core.component.upload-file.desc-max-size': '最大: {maxSize}MB',
|
|
839
|
+
'core.component.upload-file.not-image': '[{name}] アップロードされたファイルは画像ではありません',
|
|
840
|
+
'core.component.upload-file.invalid-format': '[{name}] アップロードされたファイルの形式が正しくありません: {exts}',
|
|
841
|
+
'core.component.upload-file.size-exceeded': '[{name}] 最大ファイルサイズ: {maxSize} MB',
|
|
842
|
+
'core.component.upload-file.upload-failed': 'ファイルのアップロード中にエラーが発生しました',
|
|
843
|
+
'core.component.upload-file.too-many-files': 'ファイルの選択数が多すぎます。件数を確認してください',
|
|
844
|
+
'core.component.upload-file.confirm-delete-message': 'このファイルを削除しますか?この操作は取り消せません',
|
|
845
|
+
'core.component.upload-file.confirm-delete-title': '削除の確認',
|
|
846
|
+
'core.component.upload-file.confirm-yes': '確認',
|
|
847
|
+
'core.component.upload-file.confirm-no': 'キャンセル',
|
|
848
|
+
'core.component.upload-file.no-configuration': 'SD_UPLOAD_FILE_CONFIGURATION をインジェクトするか、コンポーネントに [upload] を直接渡してください',
|
|
849
|
+
'core.component.upload-file.no-configuration-key': 'key=\'{key}\' に対応するアップロード設定が見つかりません。プロバイダーを確認するか [upload] を直接渡してください',
|
|
850
|
+
'core.component.upload-file.preview-title': '画像プレビュー',
|
|
851
|
+
// ---- Module: layout (sidebar / user menu) ----
|
|
852
|
+
'core.module.layout.user.change-password': 'パスワード変更',
|
|
853
|
+
'core.module.layout.user.logout': 'ログアウト',
|
|
854
|
+
'core.module.layout.sidebar.search': '検索',
|
|
855
|
+
// ---- Module: layout (greeting + weekday) ----
|
|
856
|
+
'core.module.layout.greeting.hello': 'こんにちは、{name}さん',
|
|
857
|
+
'core.module.layout.weekday.0': '日曜日',
|
|
858
|
+
'core.module.layout.weekday.1': '月曜日',
|
|
859
|
+
'core.module.layout.weekday.2': '火曜日',
|
|
860
|
+
'core.module.layout.weekday.3': '水曜日',
|
|
861
|
+
'core.module.layout.weekday.4': '木曜日',
|
|
862
|
+
'core.module.layout.weekday.5': '金曜日',
|
|
863
|
+
'core.module.layout.weekday.6': '土曜日',
|
|
864
|
+
'core.module.layout.today-info.format': '{weekday}、{date}',
|
|
865
|
+
// ---- Module: layout (forbidden page) ----
|
|
866
|
+
'core.module.layout.forbidden.title': 'アクセスが拒否されました',
|
|
867
|
+
'core.module.layout.forbidden.message': 'このページにアクセスする権限がありません。管理者にお問い合わせいただくか、ホームページに戻ってください',
|
|
868
|
+
'core.module.layout.forbidden.back-home': 'ホームに戻る',
|
|
869
|
+
// ---- Module: layout (not-found page) ----
|
|
870
|
+
'core.module.layout.not-found.title': '404 - ページが見つかりません',
|
|
871
|
+
'core.module.layout.not-found.message': 'お探しのページは存在しないか、削除されました。URLを確認するか、ホームページに戻って続行してください。',
|
|
872
|
+
'core.module.layout.not-found.back': '戻る',
|
|
873
|
+
// ---- Module: layout (home page) ----
|
|
874
|
+
'core.module.layout.home.tab-name': 'ホーム',
|
|
875
|
+
'core.module.layout.home.feature.data': 'データ',
|
|
876
|
+
'core.module.layout.home.feature.reports': 'レポート',
|
|
877
|
+
'core.module.layout.home.feature.users': 'ユーザー',
|
|
878
|
+
'core.module.layout.home.feature.workflow': 'ワークフロー',
|
|
879
|
+
'core.module.layout.home.feature.audit': '監査',
|
|
880
|
+
'core.module.layout.home.feature.integration': '連携',
|
|
881
|
+
// ---- Module: layout (mock fallback when SD_LAYOUT_CONFIGURATION is not provided) ----
|
|
882
|
+
'core.module.layout.mock.user.full-name': 'デモユーザー',
|
|
883
|
+
// ---- Module: generic (generic-select) ----
|
|
884
|
+
'core.module.generic.generic-select.detail-link': '詳細',
|
|
885
|
+
};
|
|
886
|
+
|
|
887
|
+
const KO_MESSAGES = {
|
|
888
|
+
'core.common.cancel': '취소',
|
|
889
|
+
'core.common.close': '닫기',
|
|
890
|
+
'core.common.reload': '페이지 새로고침',
|
|
891
|
+
'core.test.greet': '안녕하세요 {name}님',
|
|
892
|
+
// ---- Validators (pattern.model.ts) ----
|
|
893
|
+
'core.validator.email.name': '이메일',
|
|
894
|
+
'core.validator.email.error': '올바르지 않은 이메일 형식입니다',
|
|
895
|
+
'core.validator.phone.name': '전화번호',
|
|
896
|
+
'core.validator.phone.error': '올바르지 않은 전화번호 형식입니다',
|
|
897
|
+
'core.validator.phone-vn.name': 'VN 전화번호',
|
|
898
|
+
'core.validator.phone-vn.error': '올바르지 않은 전화번호 형식입니다',
|
|
899
|
+
'core.validator.cccd.name': '주민번호',
|
|
900
|
+
'core.validator.cccd.error': '올바르지 않은 주민번호 형식입니다 (12자리)',
|
|
901
|
+
'core.validator.passport.name': '여권',
|
|
902
|
+
'core.validator.passport.error': '올바르지 않은 여권번호입니다 (영문 1자 + 숫자 7자리)',
|
|
903
|
+
'core.validator.id-vn.name': '주민번호 / 여권',
|
|
904
|
+
'core.validator.id-vn.error': '올바르지 않은 주민번호 또는 여권번호입니다',
|
|
905
|
+
'core.validator.time.name': '시간',
|
|
906
|
+
'core.validator.time.error': '올바르지 않은 시간 형식입니다 (HH:mm 형식)',
|
|
907
|
+
// ---- Operators (operator.model.ts) ----
|
|
908
|
+
'core.operator.equal.display': '같음',
|
|
909
|
+
'core.operator.not-equal.display': '같지 않음',
|
|
910
|
+
'core.operator.greater-than.display': '초과',
|
|
911
|
+
'core.operator.less-than.display': '미만',
|
|
912
|
+
'core.operator.greater-or-equal.display': '이상',
|
|
913
|
+
'core.operator.less-or-equal.display': '이하',
|
|
914
|
+
'core.operator.contain.display': '포함',
|
|
915
|
+
'core.operator.not-contain.display': '포함하지 않음',
|
|
916
|
+
'core.operator.start-with.display': '~로 시작',
|
|
917
|
+
'core.operator.end-with.display': '~로 끝',
|
|
918
|
+
'core.operator.in.display': '~중 하나',
|
|
919
|
+
'core.operator.not-in.display': '~중 하나가 아님',
|
|
920
|
+
'core.operator.null.display': '비어 있음',
|
|
921
|
+
'core.operator.not-null.display': '비어 있지 않음',
|
|
922
|
+
// ---- Global error handler ----
|
|
923
|
+
'core.handler.global-error.update-title': '새로운 시스템 업데이트가 있습니다',
|
|
924
|
+
'core.handler.global-error.update-body': '현재 버전이 오래되어 리소스를 불러올 수 없습니다.\n확인을 누르면 페이지가 새로고침됩니다.',
|
|
925
|
+
// ---- Interceptor: no-internet ----
|
|
926
|
+
'core.interceptor.no-internet.offline': '네트워크 연결이 없습니다. 연결을 기다리는 중...',
|
|
927
|
+
'core.interceptor.no-internet.cors-error': '서버에 연결할 수 없습니다 (CORS 또는 설정 오류).',
|
|
928
|
+
'core.interceptor.no-internet.maintenance': '서버 점검 중입니다. 잠시 후 다시 시도해 주세요.',
|
|
929
|
+
'core.interceptor.no-internet.restored': '연결이 복구되었습니다.',
|
|
930
|
+
// ---- Service: excel ----
|
|
931
|
+
'core.excel.cannot-read-file': '파일 내용을 읽을 수 없습니다',
|
|
932
|
+
'core.excel.no-sheet': 'Excel 파일에 데이터 시트가 없습니다',
|
|
933
|
+
// ---- Service: docx ----
|
|
934
|
+
'core.docx.invalid-format': '형식이 올바르지 않습니다. DOC 또는 DOCX 형식의 템플릿을 선택해 주세요',
|
|
935
|
+
'core.docx.size-exceeded': '템플릿 파일 크기가 지원 한도를 초과했습니다. 다시 시도해 주세요',
|
|
936
|
+
'core.docx.convert-error': 'DOCX 파일 변환 중 오류가 발생했습니다',
|
|
937
|
+
// ---- Service: confirm ----
|
|
938
|
+
'core.confirm.title': '확인',
|
|
939
|
+
'core.confirm.yes': '확인',
|
|
940
|
+
'core.confirm.no': '취소',
|
|
941
|
+
'core.confirm.yes-short': '예',
|
|
942
|
+
'core.confirm.no-short': '아니오',
|
|
943
|
+
// ---- Directive: hover-copy ----
|
|
944
|
+
'core.directive.hover-copy.tooltip': '복사',
|
|
945
|
+
// ---- Forms: input ----
|
|
946
|
+
'core.form.input.required': '정보를 입력해 주세요',
|
|
947
|
+
'core.form.input.maxlength': '최대 글자수: {max}',
|
|
948
|
+
'core.form.input.invalid-pattern': '형식이 올바르지 않습니다',
|
|
949
|
+
'core.form.input.exceeded': '최대 글자수를 초과했습니다',
|
|
950
|
+
// ---- Forms: autocomplete ----
|
|
951
|
+
'core.form.autocomplete.required': '정보를 입력해 주세요',
|
|
952
|
+
// ---- Forms: chip ----
|
|
953
|
+
'core.form.chip.required': '정보를 입력해 주세요',
|
|
954
|
+
'core.form.chip.minlength': '최소 {min}개의 값을 입력해 주세요',
|
|
955
|
+
'core.form.chip.maxlength': '최대 {max}개의 값을 입력해 주세요',
|
|
956
|
+
// ---- Forms: chip-calendar ----
|
|
957
|
+
'core.form.chip-calendar.required': '정보를 입력해 주세요',
|
|
958
|
+
'core.form.chip-calendar.minlength': '최소 {min}개의 값을 입력해 주세요',
|
|
959
|
+
'core.form.chip-calendar.maxlength': '최대 {max}개의 값을 입력해 주세요',
|
|
960
|
+
// ---- Forms: date ----
|
|
961
|
+
'core.form.date.required': '정보를 입력해 주세요',
|
|
962
|
+
'core.form.date.min-date': '최소 날짜: {date}',
|
|
963
|
+
'core.form.date.max-date': '최대 날짜: {date}',
|
|
964
|
+
'core.form.date.parse-error': '구문 분석 오류: {text}',
|
|
965
|
+
'core.form.date.invalid-format': '형식이 올바르지 않습니다',
|
|
966
|
+
// ---- Forms: date-range ----
|
|
967
|
+
'core.form.date-range.required': '정보를 입력해 주세요',
|
|
968
|
+
'core.form.date-range.invalid-min': '시작일이 올바르지 않습니다 (한도 미만)',
|
|
969
|
+
'core.form.date-range.invalid-max': '종료일이 올바르지 않습니다 (한도 초과)',
|
|
970
|
+
'core.form.date-range.from': '시작',
|
|
971
|
+
'core.form.date-range.to': '~',
|
|
972
|
+
// ---- Forms: datetime ----
|
|
973
|
+
'core.form.datetime.required': '정보를 입력해 주세요',
|
|
974
|
+
'core.form.datetime.min-date': '최소 날짜: {date}',
|
|
975
|
+
'core.form.datetime.max-date': '최대 날짜: {date}',
|
|
976
|
+
'core.form.datetime.invalid-format': '형식이 올바르지 않습니다',
|
|
977
|
+
'core.form.datetime.now': '지금',
|
|
978
|
+
'core.form.datetime.confirm': '확인',
|
|
979
|
+
// ---- Forms: time-spinner ----
|
|
980
|
+
'core.form.time-spinner.hour': '시',
|
|
981
|
+
'core.form.time-spinner.minute': '분',
|
|
982
|
+
'core.form.time-spinner.second': '초',
|
|
983
|
+
'core.form.time-spinner.increase-hour': '시 증가',
|
|
984
|
+
'core.form.time-spinner.decrease-hour': '시 감소',
|
|
985
|
+
'core.form.time-spinner.increase-minute': '분 증가',
|
|
986
|
+
'core.form.time-spinner.decrease-minute': '분 감소',
|
|
987
|
+
'core.form.time-spinner.increase-second': '초 증가',
|
|
988
|
+
'core.form.time-spinner.decrease-second': '초 감소',
|
|
989
|
+
// ---- Forms: input-number ----
|
|
990
|
+
'core.form.input-number.required': '정보를 입력해 주세요',
|
|
991
|
+
'core.form.input-number.min': '값은 {min} 이상이어야 합니다',
|
|
992
|
+
'core.form.input-number.max': '값은 {max} 이하여야 합니다',
|
|
993
|
+
// ---- Forms: radio ----
|
|
994
|
+
'core.form.radio.required': '선택해 주세요',
|
|
995
|
+
// ---- Forms: select ----
|
|
996
|
+
'core.form.select.required': '선택해 주세요',
|
|
997
|
+
// ---- Forms: textarea ----
|
|
998
|
+
'core.form.textarea.required': '정보를 입력해 주세요',
|
|
999
|
+
'core.form.textarea.maxlength': '최대 글자수: {max}',
|
|
1000
|
+
'core.form.textarea.invalid-pattern': '형식이 올바르지 않습니다',
|
|
1001
|
+
'core.form.textarea.exceeded': '최대 글자수를 초과했습니다',
|
|
1002
|
+
// ---- Component: editor ----
|
|
1003
|
+
'core.component.editor.required': '내용을 입력해 주세요',
|
|
1004
|
+
'core.component.editor.maxlength': '최대 글자수: {max}',
|
|
1005
|
+
'core.component.editor.image.invalid-format': '파일 형식 ".{format}" 은(는) 허용되지 않습니다. 허용 형식: {allowed}',
|
|
1006
|
+
'core.component.editor.image.size-exceeded': '파일 크기 {sizeMB}MB가 한도 {maxSizeMB}MB를 초과합니다',
|
|
1007
|
+
'core.component.editor.image.min-width': '이미지 너비 {width}px가 최소값 {min}px 미만입니다',
|
|
1008
|
+
'core.component.editor.image.min-height': '이미지 높이 {height}px가 최소값 {min}px 미만입니다',
|
|
1009
|
+
'core.component.editor.image.max-width': '이미지 너비 {width}px가 한도 {max}px를 초과합니다',
|
|
1010
|
+
'core.component.editor.image.max-height': '이미지 높이 {height}px가 한도 {max}px를 초과합니다',
|
|
1011
|
+
'core.component.editor.image.max-per-selection': '한 번에 최대 {max}장의 이미지를 선택할 수 있습니다',
|
|
1012
|
+
// ---- Component: document-builder ----
|
|
1013
|
+
'core.component.document-builder.page-number.current': '현재 페이지 번호',
|
|
1014
|
+
'core.component.document-builder.page-number.total': '전체 페이지 수',
|
|
1015
|
+
'core.component.document-builder.ck-comment.label': '댓글',
|
|
1016
|
+
'core.component.document-builder.ck-comment.text-too-long': '텍스트가 너무 깁니다 ({length}자). 최대 {max}자입니다.',
|
|
1017
|
+
'core.component.document-builder.variable.not-allowed': '텍스트에 변수를 추가할 수 없습니다',
|
|
1018
|
+
'core.component.document-builder.variable.invalid-data': '변수 데이터가 올바르지 않습니다',
|
|
1019
|
+
// ---- Component: form-builder ----
|
|
1020
|
+
'core.component.form-builder.field-key': '필드 키',
|
|
1021
|
+
'core.component.form-builder.display': '표시',
|
|
1022
|
+
'core.component.form-builder.general': '일반',
|
|
1023
|
+
'core.component.form-builder.visible-when': '표시 조건',
|
|
1024
|
+
'core.component.form-builder.required': '필수',
|
|
1025
|
+
'core.component.form-builder.label': '라벨',
|
|
1026
|
+
'core.component.form-builder.disabled': '비활성',
|
|
1027
|
+
'core.component.form-builder.disabled-when': '비활성 조건',
|
|
1028
|
+
'core.component.form-builder.hidden-when': '숨김 조건',
|
|
1029
|
+
'core.component.form-builder.validation': '유효성 검사',
|
|
1030
|
+
'core.component.form-builder.required-when': '필수 조건',
|
|
1031
|
+
'core.component.form-builder.confirm': '확인',
|
|
1032
|
+
'core.component.form-builder.delete': '삭제',
|
|
1033
|
+
'core.component.form-builder.save': '저장',
|
|
1034
|
+
'core.component.form-builder.hint': '힌트',
|
|
1035
|
+
'core.component.form-builder.parameter': '매개변수',
|
|
1036
|
+
'core.component.form-builder.add-field': '필드 추가',
|
|
1037
|
+
'core.component.form-builder.data': '데이터',
|
|
1038
|
+
'core.component.form-builder.query-condition': '쿼리 조건',
|
|
1039
|
+
'core.component.form-builder.set-query-value': '쿼리 값 설정',
|
|
1040
|
+
'core.component.form-builder.value-source-field': '소스 필드',
|
|
1041
|
+
'core.component.form-builder.assign-parameter': '매개변수 할당',
|
|
1042
|
+
'core.component.form-builder.template-data': '템플릿 데이터',
|
|
1043
|
+
'core.component.form-builder.set-expression': '식 설정',
|
|
1044
|
+
'core.component.form-builder.condition-group': '조건 그룹',
|
|
1045
|
+
'core.component.form-builder.condition': '조건',
|
|
1046
|
+
'core.component.form-builder.layout': '레이아웃',
|
|
1047
|
+
'core.component.form-builder.maxlength': '최대 글자수',
|
|
1048
|
+
'core.component.form-builder.assign-parameter-value': '매개변수 값 할당',
|
|
1049
|
+
'core.component.form-builder.parameter-name': '매개변수 이름',
|
|
1050
|
+
'core.component.form-builder.parameter-value': '매개변수 값',
|
|
1051
|
+
'core.component.form-builder.assign-value': '값 할당',
|
|
1052
|
+
'core.component.form-builder.add-data': '데이터 추가',
|
|
1053
|
+
'core.component.form-builder.data-api': 'API 데이터',
|
|
1054
|
+
'core.component.form-builder.data-static': '정적 데이터',
|
|
1055
|
+
'core.component.form-builder.set-on-change-assign': '변경 시 값 할당 설정',
|
|
1056
|
+
'core.component.form-builder.target-field': '대상 필드',
|
|
1057
|
+
'core.component.form-builder.target-value': '대상 값',
|
|
1058
|
+
'core.component.form-builder.column-data': '열 데이터',
|
|
1059
|
+
'core.component.form-builder.add-column': '열 추가',
|
|
1060
|
+
'core.component.form-builder.column-config': '열 설정',
|
|
1061
|
+
'core.component.form-builder.column-name': '열 이름',
|
|
1062
|
+
'core.component.form-builder.width': '너비',
|
|
1063
|
+
'core.component.form-builder.data-type': '데이터 유형',
|
|
1064
|
+
'core.component.form-builder.show-when-true': 'TRUE일 때 표시',
|
|
1065
|
+
'core.component.form-builder.show-when-false': 'FALSE일 때 표시',
|
|
1066
|
+
'core.component.form-builder.column-list': '열 목록',
|
|
1067
|
+
'core.component.form-builder.yes-no': '예/아니오',
|
|
1068
|
+
'core.component.form-builder.config-validation-error-warning': '오류/경고 유효성 검사 설정',
|
|
1069
|
+
'core.component.form-builder.message-type': '메시지 유형',
|
|
1070
|
+
'core.component.form-builder.message-display': '표시 메시지',
|
|
1071
|
+
'core.component.form-builder.condition-expression': '조건식',
|
|
1072
|
+
'core.component.form-builder.add-validation': '유효성 검사 추가',
|
|
1073
|
+
'core.component.form-builder.expression': '식',
|
|
1074
|
+
'core.component.form-builder.available-methods': '사용 가능한 메서드',
|
|
1075
|
+
'core.component.form-builder.format': '형식',
|
|
1076
|
+
'core.component.form-builder.time': '시간',
|
|
1077
|
+
'core.component.form-builder.content': '내용',
|
|
1078
|
+
'core.component.form-builder.min': '최소',
|
|
1079
|
+
'core.component.form-builder.max': '최대',
|
|
1080
|
+
'core.component.form-builder.vertical': '세로',
|
|
1081
|
+
'core.component.form-builder.multiple': '다중 선택',
|
|
1082
|
+
'core.component.form-builder.default-value': '기본값',
|
|
1083
|
+
'core.component.form-builder.type': '유형',
|
|
1084
|
+
'core.component.form-builder.file': '파일',
|
|
1085
|
+
'core.component.form-builder.image': '이미지',
|
|
1086
|
+
'core.component.form-builder.max-files': '최대 파일/이미지 수',
|
|
1087
|
+
'core.component.form-builder.size-mb': '크기 (MB)',
|
|
1088
|
+
'core.component.form-builder.format-example': '형식 (예: png,jpg ...)',
|
|
1089
|
+
'core.component.form-builder.source-mobile': '소스 (모바일)',
|
|
1090
|
+
'core.component.form-builder.config-variable': '변수 설정',
|
|
1091
|
+
'core.component.form-builder.config-validation-warning-error': '경고/오류 유효성 검사 설정',
|
|
1092
|
+
'core.component.form-builder.back-to-design': '디자인으로 돌아가기',
|
|
1093
|
+
'core.component.form-builder.preview': '미리보기',
|
|
1094
|
+
'core.component.form-builder.drag-vertically': '위/아래로 드래그',
|
|
1095
|
+
'core.component.form-builder.unset-readonly': '읽기 전용 해제',
|
|
1096
|
+
'core.component.form-builder.set-readonly': '읽기 전용',
|
|
1097
|
+
'core.component.form-builder.duplicate': '복제',
|
|
1098
|
+
'core.component.form-builder.show': '표시',
|
|
1099
|
+
'core.component.form-builder.hide': '숨기기',
|
|
1100
|
+
'core.component.form-builder.flex': '플렉스',
|
|
1101
|
+
'core.component.form-builder.display-label': '표시 라벨',
|
|
1102
|
+
'core.component.form-builder.attribute': '속성',
|
|
1103
|
+
'core.component.form-builder.add-variable': '변수 추가',
|
|
1104
|
+
'core.component.form-builder.add-new': '새로 추가',
|
|
1105
|
+
'core.component.form-builder.detail': '상세',
|
|
1106
|
+
'core.component.form-builder.create-update': '생성/수정',
|
|
1107
|
+
'core.component.form-builder.default': '기본',
|
|
1108
|
+
'core.component.form-builder.show-more': '더 보기',
|
|
1109
|
+
'core.component.form-builder.show-less': '접기',
|
|
1110
|
+
'core.component.form-builder.row-overflow': '전체 크기가 12열을 초과하여 이 행으로 이동할 수 없습니다',
|
|
1111
|
+
'core.component.form-builder.upload-source.all': '전체',
|
|
1112
|
+
'core.component.form-builder.upload-source.photo-library': '라이브러리에서 선택',
|
|
1113
|
+
'core.component.form-builder.upload-source.capture': '사진 촬영',
|
|
1114
|
+
// Form-builder UI v2 (M3 redesign)
|
|
1115
|
+
'core.component.form-builder.components': '컴포넌트',
|
|
1116
|
+
'core.component.form-builder.search-components': '컴포넌트 검색…',
|
|
1117
|
+
'core.component.form-builder.view-json': 'JSON 보기',
|
|
1118
|
+
'core.component.form-builder.design': '디자인',
|
|
1119
|
+
'core.component.form-builder.preview-runtime': '미리보기 · 런타임',
|
|
1120
|
+
'core.component.form-builder.cancel': '취소',
|
|
1121
|
+
'core.component.form-builder.submit': '제출',
|
|
1122
|
+
'core.component.form-builder.empty-title': '여기에 컴포넌트를 끌어다 놓아 시작',
|
|
1123
|
+
'core.component.form-builder.empty-hint': '왼쪽 패널에서 필드를 드래그하여 양식을 만들거나 다음을 누르세요:',
|
|
1124
|
+
'core.component.form-builder.conditional': '조건부',
|
|
1125
|
+
'core.component.form-builder.group-drop-here': '필드를 여기에 놓아 이 그룹에 추가',
|
|
1126
|
+
'core.component.form-builder.hidden': '숨김',
|
|
1127
|
+
'core.component.form-builder.read-only': '읽기 전용',
|
|
1128
|
+
'core.component.form-builder.untitled': '제목 없음',
|
|
1129
|
+
'core.component.form-builder.no-selection-title': '선택 항목 없음',
|
|
1130
|
+
'core.component.form-builder.no-selection-hint': '캔버스에서 컴포넌트를 선택하여 속성을 편집하세요.',
|
|
1131
|
+
'core.component.form-builder.group-children': '하위 요소',
|
|
1132
|
+
'core.component.form-builder.group-icon': '아이콘',
|
|
1133
|
+
'core.component.form-builder.group-accent-color': '강조 색상',
|
|
1134
|
+
'core.component.form-builder.group-no-children': '필드가 아직 없습니다. 이 그룹에 필드를 추가하거나 드래그하세요.',
|
|
1135
|
+
'core.component.form-builder.break': '줄 바꿈',
|
|
1136
|
+
// ---- Component: code-editor ----
|
|
1137
|
+
'core.component.code-editor.copied': '복사되었습니다!',
|
|
1138
|
+
'core.component.code-editor.copy': '코드 복사',
|
|
1139
|
+
// ---- Component: history ----
|
|
1140
|
+
'core.component.history.by': '작성자',
|
|
1141
|
+
// ---- Component: import-excel ----
|
|
1142
|
+
'core.component.import-excel.title': 'Excel 데이터 가져오기',
|
|
1143
|
+
'core.component.import-excel.see-all': '전체 보기',
|
|
1144
|
+
'core.component.import-excel.valid-rows': '유효한 행',
|
|
1145
|
+
'core.component.import-excel.error-rows': '오류 행',
|
|
1146
|
+
'core.component.import-excel.warning-rows': '경고 행',
|
|
1147
|
+
'core.component.import-excel.valid-data': '유효한 데이터',
|
|
1148
|
+
'core.component.import-excel.download-template-tooltip': '클릭하여 템플릿 다운로드',
|
|
1149
|
+
'core.component.import-excel.upload': '업로드',
|
|
1150
|
+
'core.component.import-excel.download': '다운로드',
|
|
1151
|
+
'core.component.import-excel.confirm-save': '확인 및 저장',
|
|
1152
|
+
'core.component.import-excel.status': '상태',
|
|
1153
|
+
'core.component.import-excel.no-data-upload': '업로드된 데이터가 없습니다',
|
|
1154
|
+
'core.component.import-excel.click-here-template': '여기를 클릭하여 템플릿 다운로드',
|
|
1155
|
+
'core.component.import-excel.no-data-in-file': '파일에 데이터가 없습니다',
|
|
1156
|
+
'core.component.import-excel.row-limit': '업로드 한도는 {limit}행입니다',
|
|
1157
|
+
'core.component.import-excel.required': '필수 데이터',
|
|
1158
|
+
'core.component.import-excel.min-length': '최소 문자열 길이: {min}',
|
|
1159
|
+
'core.component.import-excel.max-length': '최대 문자열 길이: {max}',
|
|
1160
|
+
'core.component.import-excel.not-a-number': '{value} 은(는) 유효한 숫자가 아닙니다',
|
|
1161
|
+
'core.component.import-excel.below-min': '{value} 은(는) 최소값 {min} 미만입니다',
|
|
1162
|
+
'core.component.import-excel.above-max': '{value} 은(는) 최대값 {max} 초과입니다',
|
|
1163
|
+
'core.component.import-excel.invalid-bool': '유효한 값을 입력해 주세요 (true, false, 1, 0)',
|
|
1164
|
+
'core.component.import-excel.invalid-value': '값 {value} 이(가) 올바르지 않습니다',
|
|
1165
|
+
'core.component.import-excel.value-not-in-list': '값 {value} 이(가) 허용 목록 [{list}]에 없습니다',
|
|
1166
|
+
'core.component.import-excel.invalid-date-format': '날짜 {value} 이(가) 형식 {format} 과(와) 일치하지 않습니다',
|
|
1167
|
+
'core.component.import-excel.generic-error': '오류가 발생했습니다',
|
|
1168
|
+
'core.component.import-excel.notify-title': '알림',
|
|
1169
|
+
'core.component.import-excel.message-column': '메시지',
|
|
1170
|
+
'core.component.import-excel.success': '성공',
|
|
1171
|
+
// ---- Component: preview-image ----
|
|
1172
|
+
'core.component.preview-image.no-image': '이미지 정보가 없습니다',
|
|
1173
|
+
'core.component.preview-image.title': '이미지 미리보기',
|
|
1174
|
+
'core.component.preview-image.no-image-hint': '표시할 이미지가 없습니다',
|
|
1175
|
+
'core.component.preview-image.load-error': '이미지를 불러올 수 없습니다',
|
|
1176
|
+
'core.component.preview-image.load-error-hint': '이미지 파일이 삭제되었거나 경로가 유효하지 않을 수 있습니다',
|
|
1177
|
+
'core.component.preview-image.retry': '다시 시도',
|
|
1178
|
+
'core.component.preview-image.close': '닫기',
|
|
1179
|
+
'core.component.preview-image.prev': '이전 이미지',
|
|
1180
|
+
'core.component.preview-image.next': '다음 이미지',
|
|
1181
|
+
'core.component.preview-image.zoom-in': '확대',
|
|
1182
|
+
'core.component.preview-image.zoom-out': '축소',
|
|
1183
|
+
'core.component.preview-image.fit': '화면에 맞춤',
|
|
1184
|
+
'core.component.preview-image.rotate': '회전',
|
|
1185
|
+
'core.component.preview-image.download': '다운로드',
|
|
1186
|
+
'core.component.preview-image.fullscreen': '전체 화면',
|
|
1187
|
+
'core.component.preview-image.loading': '이미지를 불러오는 중...',
|
|
1188
|
+
'core.component.preview-image.kbd-hint-nav': '이미지 이동',
|
|
1189
|
+
'core.component.preview-image.kbd-hint-close': '닫기',
|
|
1190
|
+
// ---- Component: preview-pdf ----
|
|
1191
|
+
'core.component.preview-pdf.title': '문서 보기',
|
|
1192
|
+
'core.component.preview-pdf.close': '닫기',
|
|
1193
|
+
'core.component.preview-pdf.pages-count': '{count} 페이지',
|
|
1194
|
+
'core.component.preview-pdf.tab.thumbnails': '페이지',
|
|
1195
|
+
'core.component.preview-pdf.tab.outline': '목차',
|
|
1196
|
+
'core.component.preview-pdf.tab.search': '검색',
|
|
1197
|
+
'core.component.preview-pdf.first-page': '첫 페이지',
|
|
1198
|
+
'core.component.preview-pdf.prev-page': '이전 페이지',
|
|
1199
|
+
'core.component.preview-pdf.next-page': '다음 페이지',
|
|
1200
|
+
'core.component.preview-pdf.last-page': '마지막 페이지',
|
|
1201
|
+
'core.component.preview-pdf.zoom-in': '확대',
|
|
1202
|
+
'core.component.preview-pdf.zoom-out': '축소',
|
|
1203
|
+
'core.component.preview-pdf.fit-page': '페이지에 맞춤',
|
|
1204
|
+
'core.component.preview-pdf.fit-width': '너비에 맞춤',
|
|
1205
|
+
'core.component.preview-pdf.actual-size': '실제 크기',
|
|
1206
|
+
'core.component.preview-pdf.rotate': '회전',
|
|
1207
|
+
'core.component.preview-pdf.scroll-page': '한 페이지',
|
|
1208
|
+
'core.component.preview-pdf.scroll-continuous': '연속 스크롤',
|
|
1209
|
+
'core.component.preview-pdf.print': '인쇄',
|
|
1210
|
+
'core.component.preview-pdf.download': '다운로드',
|
|
1211
|
+
'core.component.preview-pdf.fullscreen': '전체 화면',
|
|
1212
|
+
'core.component.preview-pdf.toggle-sidebar': '사이드바 전환',
|
|
1213
|
+
'core.component.preview-pdf.page-of': '페이지 {current} / {total}',
|
|
1214
|
+
'core.component.preview-pdf.empty.title': '문서가 없습니다',
|
|
1215
|
+
'core.component.preview-pdf.empty.subtitle': '아직 표시할 PDF 파일이 없습니다',
|
|
1216
|
+
'core.component.preview-pdf.loading': '문서를 불러오는 중...',
|
|
1217
|
+
'core.component.preview-pdf.loading.page': '페이지 {current} / {total} 처리 중',
|
|
1218
|
+
'core.component.preview-pdf.error.invalid.title': '문서를 불러올 수 없습니다',
|
|
1219
|
+
'core.component.preview-pdf.error.invalid.body': 'PDF 파일이 손상되었을 수 있습니다. 파일을 확인하세요.',
|
|
1220
|
+
'core.component.preview-pdf.error.password.title': '보호된 문서',
|
|
1221
|
+
'core.component.preview-pdf.error.password.body': '이 PDF 파일을 열려면 비밀번호가 필요합니다.',
|
|
1222
|
+
'core.component.preview-pdf.error.network.title': '연결할 수 없습니다',
|
|
1223
|
+
'core.component.preview-pdf.error.network.body': '서버에서 파일을 불러올 수 없습니다. 나중에 다시 시도하세요.',
|
|
1224
|
+
'core.component.preview-pdf.error.unknown.title': '오류가 발생했습니다',
|
|
1225
|
+
'core.component.preview-pdf.error.unknown.body': '다시 시도하거나 원본 파일을 다운로드하여 확인하세요.',
|
|
1226
|
+
'core.component.preview-pdf.error.retry': '다시 시도',
|
|
1227
|
+
'core.component.preview-pdf.error.download-raw': '원본 다운로드',
|
|
1228
|
+
'core.component.preview-pdf.deferred.outline': '목차는 다음 버전에서 추가됩니다.',
|
|
1229
|
+
'core.component.preview-pdf.deferred.search': '검색 기능은 다음 버전에서 추가됩니다.',
|
|
1230
|
+
'core.component.preview-pdf.search': '검색',
|
|
1231
|
+
'core.component.preview-pdf.search-placeholder': '문서에서 검색...',
|
|
1232
|
+
'core.component.preview-pdf.search-case': '대소문자 구분',
|
|
1233
|
+
'core.component.preview-pdf.search-whole': '단어 단위',
|
|
1234
|
+
'core.component.preview-pdf.search-no-results': '결과 없음',
|
|
1235
|
+
'core.component.preview-pdf.search-results-count': '"{term}"에 대한 결과 {count}개',
|
|
1236
|
+
'core.component.preview-pdf.search-prev': '이전 결과',
|
|
1237
|
+
'core.component.preview-pdf.search-next': '다음 결과',
|
|
1238
|
+
'core.component.preview-pdf.search-close': '검색 닫기',
|
|
1239
|
+
// ---- Component: table ----
|
|
1240
|
+
'core.component.table.setup': '테이블 설정',
|
|
1241
|
+
'core.component.table.column-header': '열 머리글',
|
|
1242
|
+
'core.component.table.width': '너비',
|
|
1243
|
+
'core.component.table.fixed': '고정',
|
|
1244
|
+
'core.component.table.char-limit': '글자수 제한',
|
|
1245
|
+
'core.component.table.skip': '건너뛰기',
|
|
1246
|
+
'core.component.table.apply': '적용',
|
|
1247
|
+
'core.component.table.filter': '필터',
|
|
1248
|
+
'core.component.table.clear-selection': '선택 해제',
|
|
1249
|
+
'core.component.table.customize': '사용자 지정',
|
|
1250
|
+
'core.component.table.search': '검색',
|
|
1251
|
+
'core.component.table.reload': '새로고침',
|
|
1252
|
+
'core.component.table.setup-short': '설정',
|
|
1253
|
+
'core.component.table.no-results': '검색 결과가 없습니다',
|
|
1254
|
+
'core.component.table.no-results-hint': '다른 조건으로 검색하거나 필터링해 주세요',
|
|
1255
|
+
'core.component.table.choose-filter-hint': '시작하려면 필터를 선택해 주세요',
|
|
1256
|
+
'core.component.table.no-data': '데이터가 없습니다',
|
|
1257
|
+
'core.component.table.export-excel': 'Excel 내보내기',
|
|
1258
|
+
'core.component.table.export-csv': 'CSV 내보내기',
|
|
1259
|
+
'core.component.table.showing': '표시 중:',
|
|
1260
|
+
'core.component.table.paginator.first-page': '첫 페이지',
|
|
1261
|
+
'core.component.table.paginator.last-page': '마지막 페이지',
|
|
1262
|
+
'core.component.table.paginator.items-per-page': '표시 중',
|
|
1263
|
+
'core.component.table.paginator.next-page': '다음 페이지',
|
|
1264
|
+
'core.component.table.paginator.previous-page': '이전 페이지',
|
|
1265
|
+
'core.component.table.error-occurred': '오류가 발생했습니다',
|
|
1266
|
+
'core.component.table.not-an-array': '데이터가 배열이 아닙니다',
|
|
1267
|
+
'core.component.table.config.confirm-reset': '모든 설정을 기본값으로 초기화하시겠습니까',
|
|
1268
|
+
'core.component.table.popup-export.select-columns': '내보낼 열을 선택해 주세요',
|
|
1269
|
+
'core.component.table.selector-action.default-msg': '개 선택됨',
|
|
1270
|
+
'core.component.tab-router.too-many-tabs': '너무 많은 탭이 열려 있습니다.',
|
|
1271
|
+
// ---- Component: upload-file ----
|
|
1272
|
+
'core.component.upload-file.upload': '파일 업로드',
|
|
1273
|
+
'core.component.upload-file.error-occurred': '오류가 발생했습니다',
|
|
1274
|
+
'core.component.upload-file.please-upload': '파일/이미지를 업로드해 주세요',
|
|
1275
|
+
'core.component.upload-file.desc-format-and-size': '형식: {exts}, 최대: {maxSize}MB',
|
|
1276
|
+
'core.component.upload-file.desc-format': '형식: {exts}',
|
|
1277
|
+
'core.component.upload-file.desc-max-size': '최대: {maxSize}MB',
|
|
1278
|
+
'core.component.upload-file.not-image': '[{name}] 업로드한 파일이 이미지가 아닙니다',
|
|
1279
|
+
'core.component.upload-file.invalid-format': '[{name}] 업로드한 파일의 형식이 올바르지 않습니다: {exts}',
|
|
1280
|
+
'core.component.upload-file.size-exceeded': '[{name}] 최대 파일 크기: {maxSize} MB',
|
|
1281
|
+
'core.component.upload-file.upload-failed': '파일 업로드 중 오류가 발생했습니다',
|
|
1282
|
+
'core.component.upload-file.too-many-files': '파일을 너무 많이 선택했습니다. 개수를 확인해 주세요',
|
|
1283
|
+
'core.component.upload-file.confirm-delete-message': '이 파일을 삭제하시겠습니까? 이 작업은 되돌릴 수 없습니다',
|
|
1284
|
+
'core.component.upload-file.confirm-delete-title': '삭제 확인',
|
|
1285
|
+
'core.component.upload-file.confirm-yes': '확인',
|
|
1286
|
+
'core.component.upload-file.confirm-no': '취소',
|
|
1287
|
+
'core.component.upload-file.no-configuration': 'SD_UPLOAD_FILE_CONFIGURATION 을 inject 하거나 컴포넌트에 [upload] 를 직접 전달해 주세요',
|
|
1288
|
+
'core.component.upload-file.no-configuration-key': 'key=\'{key}\' 에 대한 업로드 설정을 찾을 수 없습니다. provider 를 확인하거나 [upload] 를 직접 전달해 주세요',
|
|
1289
|
+
'core.component.upload-file.preview-title': '이미지 미리보기',
|
|
1290
|
+
// ---- Module: layout (sidebar / user menu) ----
|
|
1291
|
+
'core.module.layout.user.change-password': '비밀번호 변경',
|
|
1292
|
+
'core.module.layout.user.logout': '로그아웃',
|
|
1293
|
+
'core.module.layout.sidebar.search': '검색',
|
|
1294
|
+
// ---- Module: layout (greeting + weekday) ----
|
|
1295
|
+
'core.module.layout.greeting.hello': '안녕하세요, {name}님',
|
|
1296
|
+
'core.module.layout.weekday.0': '일요일',
|
|
1297
|
+
'core.module.layout.weekday.1': '월요일',
|
|
1298
|
+
'core.module.layout.weekday.2': '화요일',
|
|
1299
|
+
'core.module.layout.weekday.3': '수요일',
|
|
1300
|
+
'core.module.layout.weekday.4': '목요일',
|
|
1301
|
+
'core.module.layout.weekday.5': '금요일',
|
|
1302
|
+
'core.module.layout.weekday.6': '토요일',
|
|
1303
|
+
'core.module.layout.today-info.format': '{weekday}, {date}',
|
|
1304
|
+
// ---- Module: layout (forbidden page) ----
|
|
1305
|
+
'core.module.layout.forbidden.title': '접근이 거부되었습니다',
|
|
1306
|
+
'core.module.layout.forbidden.message': '이 페이지에 접근할 권한이 없습니다. 관리자에게 문의하거나 홈으로 돌아가 주세요',
|
|
1307
|
+
'core.module.layout.forbidden.back-home': '홈으로 돌아가기',
|
|
1308
|
+
// ---- Module: layout (not-found page) ----
|
|
1309
|
+
'core.module.layout.not-found.title': '404 - 페이지를 찾을 수 없습니다',
|
|
1310
|
+
'core.module.layout.not-found.message': '찾으시는 페이지가 존재하지 않거나 삭제되었습니다. URL을 확인하거나 홈으로 돌아가 계속 진행해 주세요.',
|
|
1311
|
+
'core.module.layout.not-found.back': '돌아가기',
|
|
1312
|
+
// ---- Module: layout (home page) ----
|
|
1313
|
+
'core.module.layout.home.tab-name': '홈',
|
|
1314
|
+
'core.module.layout.home.feature.data': '데이터',
|
|
1315
|
+
'core.module.layout.home.feature.reports': '리포트',
|
|
1316
|
+
'core.module.layout.home.feature.users': '사용자',
|
|
1317
|
+
'core.module.layout.home.feature.workflow': '워크플로우',
|
|
1318
|
+
'core.module.layout.home.feature.audit': '감사',
|
|
1319
|
+
'core.module.layout.home.feature.integration': '연계',
|
|
1320
|
+
// ---- Module: layout (mock fallback when SD_LAYOUT_CONFIGURATION is not provided) ----
|
|
1321
|
+
'core.module.layout.mock.user.full-name': '데모 사용자',
|
|
1322
|
+
// ---- Module: generic (generic-select) ----
|
|
1323
|
+
'core.module.generic.generic-select.detail-link': '상세',
|
|
1324
|
+
};
|
|
1325
|
+
|
|
358
1326
|
const VI_MESSAGES = {
|
|
359
1327
|
'core.common.cancel': 'Hủy',
|
|
360
1328
|
'core.common.close': 'Đóng',
|
|
@@ -390,9 +1358,6 @@ const VI_MESSAGES = {
|
|
|
390
1358
|
'core.operator.not-in.display': 'Không nằm trong',
|
|
391
1359
|
'core.operator.null.display': 'Là rỗng',
|
|
392
1360
|
'core.operator.not-null.display': 'Không rỗng',
|
|
393
|
-
// ---- Utility errors (utility.extension.ts) ----
|
|
394
|
-
'core.utility.upload.invalid-format': '[{name}] File tải lên không đúng định dạng. Vui lòng chọn lại',
|
|
395
|
-
'core.utility.upload.invalid-size': '[{name}] Kích thước file không hợp lệ. Vui lòng chọn một file khác',
|
|
396
1361
|
// ---- Global error handler ----
|
|
397
1362
|
'core.handler.global-error.update-title': 'HỆ THỐNG CÓ BẢN CẬP NHẬT MỚI',
|
|
398
1363
|
'core.handler.global-error.update-body': 'Phiên bản hiện tại đã cũ và không tải được tài nguyên.\nVui lòng bấm OK để tải lại trang.',
|
|
@@ -585,6 +1550,28 @@ const VI_MESSAGES = {
|
|
|
585
1550
|
'core.component.form-builder.upload-source.all': 'Tất cả',
|
|
586
1551
|
'core.component.form-builder.upload-source.photo-library': 'Chọn từ thư viện',
|
|
587
1552
|
'core.component.form-builder.upload-source.capture': 'Chụp ảnh',
|
|
1553
|
+
// Form-builder UI v2 (M3 redesign)
|
|
1554
|
+
'core.component.form-builder.components': 'Components',
|
|
1555
|
+
'core.component.form-builder.search-components': 'Tìm component…',
|
|
1556
|
+
'core.component.form-builder.view-json': 'Xem JSON',
|
|
1557
|
+
'core.component.form-builder.design': 'Thiết kế',
|
|
1558
|
+
'core.component.form-builder.preview-runtime': 'Xem trước · Runtime',
|
|
1559
|
+
'core.component.form-builder.cancel': 'Hủy',
|
|
1560
|
+
'core.component.form-builder.submit': 'Gửi',
|
|
1561
|
+
'core.component.form-builder.empty-title': 'Kéo component vào đây để bắt đầu',
|
|
1562
|
+
'core.component.form-builder.empty-hint': 'Tạo form bằng cách kéo các trường từ panel bên trái, hoặc nhấn',
|
|
1563
|
+
'core.component.form-builder.conditional': 'Có điều kiện',
|
|
1564
|
+
'core.component.form-builder.group-drop-here': 'Kéo trường vào đây để thêm vào group',
|
|
1565
|
+
'core.component.form-builder.hidden': 'Đã ẩn',
|
|
1566
|
+
'core.component.form-builder.read-only': 'Chỉ đọc',
|
|
1567
|
+
'core.component.form-builder.untitled': 'Chưa đặt tên',
|
|
1568
|
+
'core.component.form-builder.no-selection-title': 'Chưa chọn component nào',
|
|
1569
|
+
'core.component.form-builder.no-selection-hint': 'Chọn một component trên canvas để chỉnh sửa thuộc tính.',
|
|
1570
|
+
'core.component.form-builder.group-children': 'Thành phần con',
|
|
1571
|
+
'core.component.form-builder.group-icon': 'Icon',
|
|
1572
|
+
'core.component.form-builder.group-accent-color': 'Màu nhấn',
|
|
1573
|
+
'core.component.form-builder.group-no-children': 'Chưa có trường nào. Thêm hoặc kéo trường vào group này.',
|
|
1574
|
+
'core.component.form-builder.break': 'Ngắt dòng',
|
|
588
1575
|
// ---- Component: code-editor ----
|
|
589
1576
|
'core.component.code-editor.copied': 'Đã copy!',
|
|
590
1577
|
'core.component.code-editor.copy': 'Copy code',
|
|
@@ -623,6 +1610,71 @@ const VI_MESSAGES = {
|
|
|
623
1610
|
// ---- Component: preview-image ----
|
|
624
1611
|
'core.component.preview-image.no-image': 'Không có thông tin ảnh',
|
|
625
1612
|
'core.component.preview-image.title': 'Xem ảnh',
|
|
1613
|
+
'core.component.preview-image.no-image-hint': 'Chưa có ảnh nào để hiển thị',
|
|
1614
|
+
'core.component.preview-image.load-error': 'Không tải được ảnh',
|
|
1615
|
+
'core.component.preview-image.load-error-hint': 'File ảnh có thể đã bị xóa hoặc đường dẫn không hợp lệ',
|
|
1616
|
+
'core.component.preview-image.retry': 'Thử lại',
|
|
1617
|
+
'core.component.preview-image.close': 'Đóng',
|
|
1618
|
+
'core.component.preview-image.prev': 'Ảnh trước',
|
|
1619
|
+
'core.component.preview-image.next': 'Ảnh tiếp theo',
|
|
1620
|
+
'core.component.preview-image.zoom-in': 'Phóng to',
|
|
1621
|
+
'core.component.preview-image.zoom-out': 'Thu nhỏ',
|
|
1622
|
+
'core.component.preview-image.fit': 'Vừa khung',
|
|
1623
|
+
'core.component.preview-image.rotate': 'Xoay',
|
|
1624
|
+
'core.component.preview-image.download': 'Tải xuống',
|
|
1625
|
+
'core.component.preview-image.fullscreen': 'Toàn màn hình',
|
|
1626
|
+
'core.component.preview-image.loading': 'Đang tải ảnh...',
|
|
1627
|
+
'core.component.preview-image.kbd-hint-nav': 'chuyển ảnh',
|
|
1628
|
+
'core.component.preview-image.kbd-hint-close': 'đóng',
|
|
1629
|
+
// ---- Component: preview-pdf ----
|
|
1630
|
+
'core.component.preview-pdf.title': 'Xem tài liệu',
|
|
1631
|
+
'core.component.preview-pdf.close': 'Đóng',
|
|
1632
|
+
'core.component.preview-pdf.pages-count': '{count} trang',
|
|
1633
|
+
'core.component.preview-pdf.tab.thumbnails': 'Trang',
|
|
1634
|
+
'core.component.preview-pdf.tab.outline': 'Mục lục',
|
|
1635
|
+
'core.component.preview-pdf.tab.search': 'Tìm',
|
|
1636
|
+
'core.component.preview-pdf.first-page': 'Trang đầu',
|
|
1637
|
+
'core.component.preview-pdf.prev-page': 'Trang trước',
|
|
1638
|
+
'core.component.preview-pdf.next-page': 'Trang tiếp',
|
|
1639
|
+
'core.component.preview-pdf.last-page': 'Trang cuối',
|
|
1640
|
+
'core.component.preview-pdf.zoom-in': 'Phóng to',
|
|
1641
|
+
'core.component.preview-pdf.zoom-out': 'Thu nhỏ',
|
|
1642
|
+
'core.component.preview-pdf.fit-page': 'Vừa trang',
|
|
1643
|
+
'core.component.preview-pdf.fit-width': 'Vừa rộng',
|
|
1644
|
+
'core.component.preview-pdf.actual-size': 'Kích thước thật',
|
|
1645
|
+
'core.component.preview-pdf.rotate': 'Xoay',
|
|
1646
|
+
'core.component.preview-pdf.scroll-page': 'Từng trang',
|
|
1647
|
+
'core.component.preview-pdf.scroll-continuous': 'Cuộn liên tục',
|
|
1648
|
+
'core.component.preview-pdf.print': 'In',
|
|
1649
|
+
'core.component.preview-pdf.download': 'Tải xuống',
|
|
1650
|
+
'core.component.preview-pdf.fullscreen': 'Toàn màn hình',
|
|
1651
|
+
'core.component.preview-pdf.toggle-sidebar': 'Hiện/ẩn thanh bên',
|
|
1652
|
+
'core.component.preview-pdf.page-of': 'trang {current} / {total}',
|
|
1653
|
+
'core.component.preview-pdf.empty.title': 'Không có tài liệu',
|
|
1654
|
+
'core.component.preview-pdf.empty.subtitle': 'Chưa có file PDF nào để hiển thị',
|
|
1655
|
+
'core.component.preview-pdf.loading': 'Đang tải tài liệu...',
|
|
1656
|
+
'core.component.preview-pdf.loading.page': 'Đang xử lý trang {current} / {total}',
|
|
1657
|
+
'core.component.preview-pdf.error.invalid.title': 'Không tải được tài liệu',
|
|
1658
|
+
'core.component.preview-pdf.error.invalid.body': 'File PDF có thể bị hỏng. Vui lòng kiểm tra lại file.',
|
|
1659
|
+
'core.component.preview-pdf.error.password.title': 'Tài liệu được bảo vệ',
|
|
1660
|
+
'core.component.preview-pdf.error.password.body': 'File PDF này yêu cầu mật khẩu để mở.',
|
|
1661
|
+
'core.component.preview-pdf.error.network.title': 'Không kết nối được',
|
|
1662
|
+
'core.component.preview-pdf.error.network.body': 'Không thể tải file từ máy chủ. Vui lòng thử lại sau.',
|
|
1663
|
+
'core.component.preview-pdf.error.unknown.title': 'Đã có lỗi xảy ra',
|
|
1664
|
+
'core.component.preview-pdf.error.unknown.body': 'Vui lòng thử lại hoặc tải file gốc về để xem.',
|
|
1665
|
+
'core.component.preview-pdf.error.retry': 'Thử lại',
|
|
1666
|
+
'core.component.preview-pdf.error.download-raw': 'Tải file gốc',
|
|
1667
|
+
'core.component.preview-pdf.deferred.outline': 'Mục lục sẽ được bổ sung trong phiên bản kế tiếp.',
|
|
1668
|
+
'core.component.preview-pdf.deferred.search': 'Tính năng tìm kiếm sẽ được bổ sung trong phiên bản kế tiếp.',
|
|
1669
|
+
'core.component.preview-pdf.search': 'Tìm kiếm',
|
|
1670
|
+
'core.component.preview-pdf.search-placeholder': 'Tìm trong tài liệu...',
|
|
1671
|
+
'core.component.preview-pdf.search-case': 'Phân biệt hoa thường',
|
|
1672
|
+
'core.component.preview-pdf.search-whole': 'Từ nguyên',
|
|
1673
|
+
'core.component.preview-pdf.search-no-results': 'Không tìm thấy',
|
|
1674
|
+
'core.component.preview-pdf.search-results-count': '{count} kết quả cho "{term}"',
|
|
1675
|
+
'core.component.preview-pdf.search-prev': 'Kết quả trước',
|
|
1676
|
+
'core.component.preview-pdf.search-next': 'Kết quả tiếp',
|
|
1677
|
+
'core.component.preview-pdf.search-close': 'Đóng tìm kiếm',
|
|
626
1678
|
// ---- Component: table ----
|
|
627
1679
|
'core.component.table.setup': 'Thiết lập bảng',
|
|
628
1680
|
'core.component.table.column-header': 'Tiêu đề cột',
|
|
@@ -698,44 +1750,512 @@ const VI_MESSAGES = {
|
|
|
698
1750
|
'core.module.layout.not-found.back': 'Quay trở lại',
|
|
699
1751
|
// ---- Module: layout (home page) ----
|
|
700
1752
|
'core.module.layout.home.tab-name': 'Trang chủ',
|
|
701
|
-
'core.module.layout.home.
|
|
702
|
-
'core.module.layout.home.
|
|
1753
|
+
'core.module.layout.home.feature.data': 'Dữ liệu',
|
|
1754
|
+
'core.module.layout.home.feature.reports': 'Báo cáo',
|
|
1755
|
+
'core.module.layout.home.feature.users': 'Người dùng',
|
|
1756
|
+
'core.module.layout.home.feature.workflow': 'Quy trình',
|
|
1757
|
+
'core.module.layout.home.feature.audit': 'Kiểm toán',
|
|
1758
|
+
'core.module.layout.home.feature.integration': 'Tích hợp',
|
|
1759
|
+
// ---- Module: layout (mock fallback khi không provide SD_LAYOUT_CONFIGURATION) ----
|
|
1760
|
+
'core.module.layout.mock.user.full-name': 'Người dùng demo',
|
|
703
1761
|
// ---- Module: generic (generic-select) ----
|
|
704
1762
|
'core.module.generic.generic-select.detail-link': 'chi tiết',
|
|
705
1763
|
};
|
|
706
1764
|
|
|
707
|
-
const
|
|
1765
|
+
const ZH_MESSAGES = {
|
|
1766
|
+
'core.common.cancel': '取消',
|
|
1767
|
+
'core.common.close': '关闭',
|
|
1768
|
+
'core.common.reload': '重新加载页面',
|
|
1769
|
+
'core.test.greet': '你好 {name}',
|
|
1770
|
+
// ---- Validators (pattern.model.ts) ----
|
|
1771
|
+
'core.validator.email.name': '邮箱',
|
|
1772
|
+
'core.validator.email.error': '邮箱格式不正确',
|
|
1773
|
+
'core.validator.phone.name': '电话',
|
|
1774
|
+
'core.validator.phone.error': '电话号码格式不正确',
|
|
1775
|
+
'core.validator.phone-vn.name': '越南电话',
|
|
1776
|
+
'core.validator.phone-vn.error': '电话号码格式不正确',
|
|
1777
|
+
'core.validator.cccd.name': '身份证号',
|
|
1778
|
+
'core.validator.cccd.error': '身份证号格式不正确(12位数字)',
|
|
1779
|
+
'core.validator.passport.name': '护照',
|
|
1780
|
+
'core.validator.passport.error': '护照号码格式不正确(1个字母 + 7位数字)',
|
|
1781
|
+
'core.validator.id-vn.name': '身份证 / 护照',
|
|
1782
|
+
'core.validator.id-vn.error': '身份证或护照号码格式不正确',
|
|
1783
|
+
'core.validator.time.name': '时间',
|
|
1784
|
+
'core.validator.time.error': '时间格式不正确(HH:mm 格式)',
|
|
1785
|
+
// ---- Operators (operator.model.ts) ----
|
|
1786
|
+
'core.operator.equal.display': '等于',
|
|
1787
|
+
'core.operator.not-equal.display': '不等于',
|
|
1788
|
+
'core.operator.greater-than.display': '大于',
|
|
1789
|
+
'core.operator.less-than.display': '小于',
|
|
1790
|
+
'core.operator.greater-or-equal.display': '大于或等于',
|
|
1791
|
+
'core.operator.less-or-equal.display': '小于或等于',
|
|
1792
|
+
'core.operator.contain.display': '包含',
|
|
1793
|
+
'core.operator.not-contain.display': '不包含',
|
|
1794
|
+
'core.operator.start-with.display': '开始于',
|
|
1795
|
+
'core.operator.end-with.display': '结束于',
|
|
1796
|
+
'core.operator.in.display': '属于',
|
|
1797
|
+
'core.operator.not-in.display': '不属于',
|
|
1798
|
+
'core.operator.null.display': '为空',
|
|
1799
|
+
'core.operator.not-null.display': '不为空',
|
|
1800
|
+
// ---- Global error handler ----
|
|
1801
|
+
'core.handler.global-error.update-title': '系统有新的更新',
|
|
1802
|
+
'core.handler.global-error.update-body': '当前版本已过期,无法加载资源。\n请点击确定重新加载页面。',
|
|
1803
|
+
// ---- Interceptor: no-internet ----
|
|
1804
|
+
'core.interceptor.no-internet.offline': '没有网络连接,等待连接中...',
|
|
1805
|
+
'core.interceptor.no-internet.cors-error': '无法连接到服务器(CORS 或配置错误)。',
|
|
1806
|
+
'core.interceptor.no-internet.maintenance': '服务器正在维护中,请稍后再试。',
|
|
1807
|
+
'core.interceptor.no-internet.restored': '网络连接已恢复。',
|
|
1808
|
+
// ---- Service: excel ----
|
|
1809
|
+
'core.excel.cannot-read-file': '无法读取文件内容',
|
|
1810
|
+
'core.excel.no-sheet': 'Excel 文件没有数据表',
|
|
1811
|
+
// ---- Service: docx ----
|
|
1812
|
+
'core.docx.invalid-format': '格式不正确,请选择 DOC 或 DOCX 格式的模板',
|
|
1813
|
+
'core.docx.size-exceeded': '模板文件大小超出支持范围,请重试',
|
|
1814
|
+
'core.docx.convert-error': '转换 DOCX 文件时发生错误',
|
|
1815
|
+
// ---- Service: confirm ----
|
|
1816
|
+
'core.confirm.title': '确认',
|
|
1817
|
+
'core.confirm.yes': '确定',
|
|
1818
|
+
'core.confirm.no': '取消',
|
|
1819
|
+
'core.confirm.yes-short': '是',
|
|
1820
|
+
'core.confirm.no-short': '否',
|
|
1821
|
+
// ---- Directive: hover-copy ----
|
|
1822
|
+
'core.directive.hover-copy.tooltip': '复制',
|
|
1823
|
+
// ---- Forms: input ----
|
|
1824
|
+
'core.form.input.required': '请输入内容',
|
|
1825
|
+
'core.form.input.maxlength': '最大字符数: {max}',
|
|
1826
|
+
'core.form.input.invalid-pattern': '格式不正确',
|
|
1827
|
+
'core.form.input.exceeded': '已超过最大字符数',
|
|
1828
|
+
// ---- Forms: autocomplete ----
|
|
1829
|
+
'core.form.autocomplete.required': '请输入内容',
|
|
1830
|
+
// ---- Forms: chip ----
|
|
1831
|
+
'core.form.chip.required': '请输入内容',
|
|
1832
|
+
'core.form.chip.minlength': '请至少输入 {min} 个值',
|
|
1833
|
+
'core.form.chip.maxlength': '最多输入 {max} 个值',
|
|
1834
|
+
// ---- Forms: chip-calendar ----
|
|
1835
|
+
'core.form.chip-calendar.required': '请输入内容',
|
|
1836
|
+
'core.form.chip-calendar.minlength': '请至少输入 {min} 个值',
|
|
1837
|
+
'core.form.chip-calendar.maxlength': '最多输入 {max} 个值',
|
|
1838
|
+
// ---- Forms: date ----
|
|
1839
|
+
'core.form.date.required': '请输入内容',
|
|
1840
|
+
'core.form.date.min-date': '最小日期: {date}',
|
|
1841
|
+
'core.form.date.max-date': '最大日期: {date}',
|
|
1842
|
+
'core.form.date.parse-error': '解析错误: {text}',
|
|
1843
|
+
'core.form.date.invalid-format': '格式不正确',
|
|
1844
|
+
// ---- Forms: date-range ----
|
|
1845
|
+
'core.form.date-range.required': '请输入内容',
|
|
1846
|
+
'core.form.date-range.invalid-min': '开始日期无效(低于限制)',
|
|
1847
|
+
'core.form.date-range.invalid-max': '结束日期无效(高于限制)',
|
|
1848
|
+
'core.form.date-range.from': '从',
|
|
1849
|
+
'core.form.date-range.to': '至',
|
|
1850
|
+
// ---- Forms: datetime ----
|
|
1851
|
+
'core.form.datetime.required': '请输入内容',
|
|
1852
|
+
'core.form.datetime.min-date': '最小日期: {date}',
|
|
1853
|
+
'core.form.datetime.max-date': '最大日期: {date}',
|
|
1854
|
+
'core.form.datetime.invalid-format': '格式不正确',
|
|
1855
|
+
'core.form.datetime.now': '现在',
|
|
1856
|
+
'core.form.datetime.confirm': '确认',
|
|
1857
|
+
// ---- Forms: time-spinner ----
|
|
1858
|
+
'core.form.time-spinner.hour': '时',
|
|
1859
|
+
'core.form.time-spinner.minute': '分',
|
|
1860
|
+
'core.form.time-spinner.second': '秒',
|
|
1861
|
+
'core.form.time-spinner.increase-hour': '增加小时',
|
|
1862
|
+
'core.form.time-spinner.decrease-hour': '减少小时',
|
|
1863
|
+
'core.form.time-spinner.increase-minute': '增加分钟',
|
|
1864
|
+
'core.form.time-spinner.decrease-minute': '减少分钟',
|
|
1865
|
+
'core.form.time-spinner.increase-second': '增加秒',
|
|
1866
|
+
'core.form.time-spinner.decrease-second': '减少秒',
|
|
1867
|
+
// ---- Forms: input-number ----
|
|
1868
|
+
'core.form.input-number.required': '请输入内容',
|
|
1869
|
+
'core.form.input-number.min': '值不能小于 {min}',
|
|
1870
|
+
'core.form.input-number.max': '值不能大于 {max}',
|
|
1871
|
+
// ---- Forms: radio ----
|
|
1872
|
+
'core.form.radio.required': '请选择',
|
|
1873
|
+
// ---- Forms: select ----
|
|
1874
|
+
'core.form.select.required': '请选择',
|
|
1875
|
+
// ---- Forms: textarea ----
|
|
1876
|
+
'core.form.textarea.required': '请输入内容',
|
|
1877
|
+
'core.form.textarea.maxlength': '最大字符数: {max}',
|
|
1878
|
+
'core.form.textarea.invalid-pattern': '格式不正确',
|
|
1879
|
+
'core.form.textarea.exceeded': '已超过最大字符数',
|
|
1880
|
+
// ---- Component: editor ----
|
|
1881
|
+
'core.component.editor.required': '请输入内容',
|
|
1882
|
+
'core.component.editor.maxlength': '最大字符数: {max}',
|
|
1883
|
+
'core.component.editor.image.invalid-format': '不允许的文件格式 ".{format}"。允许的格式: {allowed}',
|
|
1884
|
+
'core.component.editor.image.size-exceeded': '文件大小 {sizeMB}MB 超过限制 {maxSizeMB}MB',
|
|
1885
|
+
'core.component.editor.image.min-width': '图片宽度 {width}px 低于最小值 {min}px',
|
|
1886
|
+
'core.component.editor.image.min-height': '图片高度 {height}px 低于最小值 {min}px',
|
|
1887
|
+
'core.component.editor.image.max-width': '图片宽度 {width}px 超过限制 {max}px',
|
|
1888
|
+
'core.component.editor.image.max-height': '图片高度 {height}px 超过限制 {max}px',
|
|
1889
|
+
'core.component.editor.image.max-per-selection': '每次最多选择 {max} 张图片',
|
|
1890
|
+
// ---- Component: document-builder ----
|
|
1891
|
+
'core.component.document-builder.page-number.current': '当前页码',
|
|
1892
|
+
'core.component.document-builder.page-number.total': '总页数',
|
|
1893
|
+
'core.component.document-builder.ck-comment.label': '评论',
|
|
1894
|
+
'core.component.document-builder.ck-comment.text-too-long': '文本过长({length} 字符)。最多 {max} 字符。',
|
|
1895
|
+
'core.component.document-builder.variable.not-allowed': '不允许在文本中添加变量',
|
|
1896
|
+
'core.component.document-builder.variable.invalid-data': '变量数据无效',
|
|
1897
|
+
// ---- Component: form-builder ----
|
|
1898
|
+
'core.component.form-builder.field-key': '字段键',
|
|
1899
|
+
'core.component.form-builder.display': '显示',
|
|
1900
|
+
'core.component.form-builder.general': '常规',
|
|
1901
|
+
'core.component.form-builder.visible-when': '显示条件',
|
|
1902
|
+
'core.component.form-builder.required': '必填',
|
|
1903
|
+
'core.component.form-builder.label': '标签',
|
|
1904
|
+
'core.component.form-builder.disabled': '禁用',
|
|
1905
|
+
'core.component.form-builder.disabled-when': '禁用条件',
|
|
1906
|
+
'core.component.form-builder.hidden-when': '隐藏条件',
|
|
1907
|
+
'core.component.form-builder.validation': '校验',
|
|
1908
|
+
'core.component.form-builder.required-when': '必填条件',
|
|
1909
|
+
'core.component.form-builder.confirm': '确认',
|
|
1910
|
+
'core.component.form-builder.delete': '删除',
|
|
1911
|
+
'core.component.form-builder.save': '保存',
|
|
1912
|
+
'core.component.form-builder.hint': '提示',
|
|
1913
|
+
'core.component.form-builder.parameter': '参数',
|
|
1914
|
+
'core.component.form-builder.add-field': '添加字段',
|
|
1915
|
+
'core.component.form-builder.data': '数据',
|
|
1916
|
+
'core.component.form-builder.query-condition': '查询条件',
|
|
1917
|
+
'core.component.form-builder.set-query-value': '设置查询值',
|
|
1918
|
+
'core.component.form-builder.value-source-field': '取值字段',
|
|
1919
|
+
'core.component.form-builder.assign-parameter': '分配参数',
|
|
1920
|
+
'core.component.form-builder.template-data': '模板数据',
|
|
1921
|
+
'core.component.form-builder.set-expression': '设置表达式',
|
|
1922
|
+
'core.component.form-builder.condition-group': '条件组',
|
|
1923
|
+
'core.component.form-builder.condition': '条件',
|
|
1924
|
+
'core.component.form-builder.layout': '布局',
|
|
1925
|
+
'core.component.form-builder.maxlength': '最大字符数',
|
|
1926
|
+
'core.component.form-builder.assign-parameter-value': '分配参数值',
|
|
1927
|
+
'core.component.form-builder.parameter-name': '参数名',
|
|
1928
|
+
'core.component.form-builder.parameter-value': '参数值',
|
|
1929
|
+
'core.component.form-builder.assign-value': '赋值',
|
|
1930
|
+
'core.component.form-builder.add-data': '添加数据',
|
|
1931
|
+
'core.component.form-builder.data-api': 'API 数据',
|
|
1932
|
+
'core.component.form-builder.data-static': '静态数据',
|
|
1933
|
+
'core.component.form-builder.set-on-change-assign': '设置变更时赋值',
|
|
1934
|
+
'core.component.form-builder.target-field': '目标字段',
|
|
1935
|
+
'core.component.form-builder.target-value': '目标值',
|
|
1936
|
+
'core.component.form-builder.column-data': '列数据',
|
|
1937
|
+
'core.component.form-builder.add-column': '添加列',
|
|
1938
|
+
'core.component.form-builder.column-config': '列配置',
|
|
1939
|
+
'core.component.form-builder.column-name': '列名',
|
|
1940
|
+
'core.component.form-builder.width': '宽度',
|
|
1941
|
+
'core.component.form-builder.data-type': '数据类型',
|
|
1942
|
+
'core.component.form-builder.show-when-true': '为 TRUE 时显示',
|
|
1943
|
+
'core.component.form-builder.show-when-false': '为 FALSE 时显示',
|
|
1944
|
+
'core.component.form-builder.column-list': '列列表',
|
|
1945
|
+
'core.component.form-builder.yes-no': '是/否',
|
|
1946
|
+
'core.component.form-builder.config-validation-error-warning': '配置错误/警告校验',
|
|
1947
|
+
'core.component.form-builder.message-type': '消息类型',
|
|
1948
|
+
'core.component.form-builder.message-display': '显示消息',
|
|
1949
|
+
'core.component.form-builder.condition-expression': '条件表达式',
|
|
1950
|
+
'core.component.form-builder.add-validation': '添加校验',
|
|
1951
|
+
'core.component.form-builder.expression': '表达式',
|
|
1952
|
+
'core.component.form-builder.available-methods': '可用方法',
|
|
1953
|
+
'core.component.form-builder.format': '格式',
|
|
1954
|
+
'core.component.form-builder.time': '时间',
|
|
1955
|
+
'core.component.form-builder.content': '内容',
|
|
1956
|
+
'core.component.form-builder.min': '最小值',
|
|
1957
|
+
'core.component.form-builder.max': '最大值',
|
|
1958
|
+
'core.component.form-builder.vertical': '垂直',
|
|
1959
|
+
'core.component.form-builder.multiple': '多选',
|
|
1960
|
+
'core.component.form-builder.default-value': '默认值',
|
|
1961
|
+
'core.component.form-builder.type': '类型',
|
|
1962
|
+
'core.component.form-builder.file': '文件',
|
|
1963
|
+
'core.component.form-builder.image': '图片',
|
|
1964
|
+
'core.component.form-builder.max-files': '最大文件/图片数',
|
|
1965
|
+
'core.component.form-builder.size-mb': '大小 (MB)',
|
|
1966
|
+
'core.component.form-builder.format-example': '格式(例如: png,jpg ...)',
|
|
1967
|
+
'core.component.form-builder.source-mobile': '来源(移动端)',
|
|
1968
|
+
'core.component.form-builder.config-variable': '配置变量',
|
|
1969
|
+
'core.component.form-builder.config-validation-warning-error': '配置警告/错误校验',
|
|
1970
|
+
'core.component.form-builder.back-to-design': '返回设计',
|
|
1971
|
+
'core.component.form-builder.preview': '预览',
|
|
1972
|
+
'core.component.form-builder.drag-vertically': '上下拖动',
|
|
1973
|
+
'core.component.form-builder.unset-readonly': '取消只读',
|
|
1974
|
+
'core.component.form-builder.set-readonly': '只读',
|
|
1975
|
+
'core.component.form-builder.duplicate': '复制',
|
|
1976
|
+
'core.component.form-builder.show': '显示',
|
|
1977
|
+
'core.component.form-builder.hide': '隐藏',
|
|
1978
|
+
'core.component.form-builder.flex': '弹性',
|
|
1979
|
+
'core.component.form-builder.display-label': '显示标签',
|
|
1980
|
+
'core.component.form-builder.attribute': '属性',
|
|
1981
|
+
'core.component.form-builder.add-variable': '添加变量',
|
|
1982
|
+
'core.component.form-builder.add-new': '新增',
|
|
1983
|
+
'core.component.form-builder.detail': '详情',
|
|
1984
|
+
'core.component.form-builder.create-update': '新建/更新',
|
|
1985
|
+
'core.component.form-builder.default': '默认',
|
|
1986
|
+
'core.component.form-builder.show-more': '查看更多',
|
|
1987
|
+
'core.component.form-builder.show-less': '收起',
|
|
1988
|
+
'core.component.form-builder.row-overflow': '无法移动到该行,因为总宽度超过 12 列',
|
|
1989
|
+
'core.component.form-builder.upload-source.all': '全部',
|
|
1990
|
+
'core.component.form-builder.upload-source.photo-library': '从相册选择',
|
|
1991
|
+
'core.component.form-builder.upload-source.capture': '拍照',
|
|
1992
|
+
// Form-builder UI v2 (M3 redesign)
|
|
1993
|
+
'core.component.form-builder.components': '组件',
|
|
1994
|
+
'core.component.form-builder.search-components': '搜索组件…',
|
|
1995
|
+
'core.component.form-builder.view-json': '查看 JSON',
|
|
1996
|
+
'core.component.form-builder.design': '设计',
|
|
1997
|
+
'core.component.form-builder.preview-runtime': '预览 · 运行时',
|
|
1998
|
+
'core.component.form-builder.cancel': '取消',
|
|
1999
|
+
'core.component.form-builder.submit': '提交',
|
|
2000
|
+
'core.component.form-builder.empty-title': '拖动组件到此处开始',
|
|
2001
|
+
'core.component.form-builder.empty-hint': '从左侧面板拖动字段构建表单,或按',
|
|
2002
|
+
'core.component.form-builder.conditional': '条件',
|
|
2003
|
+
'core.component.form-builder.group-drop-here': '将字段拖到此处以添加到该分组',
|
|
2004
|
+
'core.component.form-builder.hidden': '已隐藏',
|
|
2005
|
+
'core.component.form-builder.read-only': '只读',
|
|
2006
|
+
'core.component.form-builder.untitled': '未命名',
|
|
2007
|
+
'core.component.form-builder.no-selection-title': '未选中任何项',
|
|
2008
|
+
'core.component.form-builder.no-selection-hint': '在画布上选择一个组件以编辑其属性。',
|
|
2009
|
+
'core.component.form-builder.group-children': '子项',
|
|
2010
|
+
'core.component.form-builder.group-icon': '图标',
|
|
2011
|
+
'core.component.form-builder.group-accent-color': '强调色',
|
|
2012
|
+
'core.component.form-builder.group-no-children': '尚无字段。请向此分组添加或拖入字段。',
|
|
2013
|
+
'core.component.form-builder.break': '换行',
|
|
2014
|
+
// ---- Component: code-editor ----
|
|
2015
|
+
'core.component.code-editor.copied': '已复制!',
|
|
2016
|
+
'core.component.code-editor.copy': '复制代码',
|
|
2017
|
+
// ---- Component: history ----
|
|
2018
|
+
'core.component.history.by': '操作人',
|
|
2019
|
+
// ---- Component: import-excel ----
|
|
2020
|
+
'core.component.import-excel.title': '导入 Excel 数据',
|
|
2021
|
+
'core.component.import-excel.see-all': '查看全部',
|
|
2022
|
+
'core.component.import-excel.valid-rows': '有效行数',
|
|
2023
|
+
'core.component.import-excel.error-rows': '错误行数',
|
|
2024
|
+
'core.component.import-excel.warning-rows': '警告行数',
|
|
2025
|
+
'core.component.import-excel.valid-data': '有效数据',
|
|
2026
|
+
'core.component.import-excel.download-template-tooltip': '点击下载模板',
|
|
2027
|
+
'core.component.import-excel.upload': '上传',
|
|
2028
|
+
'core.component.import-excel.download': '下载',
|
|
2029
|
+
'core.component.import-excel.confirm-save': '确认并保存',
|
|
2030
|
+
'core.component.import-excel.status': '状态',
|
|
2031
|
+
'core.component.import-excel.no-data-upload': '未上传任何数据',
|
|
2032
|
+
'core.component.import-excel.click-here-template': '点击此处下载模板',
|
|
2033
|
+
'core.component.import-excel.no-data-in-file': '文件中没有数据',
|
|
2034
|
+
'core.component.import-excel.row-limit': '上传上限为 {limit} 行',
|
|
2035
|
+
'core.component.import-excel.required': '必填数据',
|
|
2036
|
+
'core.component.import-excel.min-length': '最小字符串长度: {min}',
|
|
2037
|
+
'core.component.import-excel.max-length': '最大字符串长度: {max}',
|
|
2038
|
+
'core.component.import-excel.not-a-number': '{value} 不是有效的数字',
|
|
2039
|
+
'core.component.import-excel.below-min': '{value} 低于最小值: {min}',
|
|
2040
|
+
'core.component.import-excel.above-max': '{value} 高于最大值: {max}',
|
|
2041
|
+
'core.component.import-excel.invalid-bool': '请输入有效值 (true, false, 1, 0)',
|
|
2042
|
+
'core.component.import-excel.invalid-value': '值 {value} 无效',
|
|
2043
|
+
'core.component.import-excel.value-not-in-list': '值 {value} 不在允许列表 [{list}] 中',
|
|
2044
|
+
'core.component.import-excel.invalid-date-format': '日期 {value} 不符合格式 {format}',
|
|
2045
|
+
'core.component.import-excel.generic-error': '发生错误',
|
|
2046
|
+
'core.component.import-excel.notify-title': '通知',
|
|
2047
|
+
'core.component.import-excel.message-column': '消息',
|
|
2048
|
+
'core.component.import-excel.success': '成功',
|
|
2049
|
+
// ---- Component: preview-image ----
|
|
2050
|
+
'core.component.preview-image.no-image': '没有图片信息',
|
|
2051
|
+
'core.component.preview-image.title': '图片预览',
|
|
2052
|
+
'core.component.preview-image.no-image-hint': '暂无可显示的图片',
|
|
2053
|
+
'core.component.preview-image.load-error': '无法加载图片',
|
|
2054
|
+
'core.component.preview-image.load-error-hint': '图片文件可能已被删除或路径无效',
|
|
2055
|
+
'core.component.preview-image.retry': '重试',
|
|
2056
|
+
'core.component.preview-image.close': '关闭',
|
|
2057
|
+
'core.component.preview-image.prev': '上一张',
|
|
2058
|
+
'core.component.preview-image.next': '下一张',
|
|
2059
|
+
'core.component.preview-image.zoom-in': '放大',
|
|
2060
|
+
'core.component.preview-image.zoom-out': '缩小',
|
|
2061
|
+
'core.component.preview-image.fit': '适应屏幕',
|
|
2062
|
+
'core.component.preview-image.rotate': '旋转',
|
|
2063
|
+
'core.component.preview-image.download': '下载',
|
|
2064
|
+
'core.component.preview-image.fullscreen': '全屏',
|
|
2065
|
+
'core.component.preview-image.loading': '正在加载图片...',
|
|
2066
|
+
'core.component.preview-image.kbd-hint-nav': '切换图片',
|
|
2067
|
+
'core.component.preview-image.kbd-hint-close': '关闭',
|
|
2068
|
+
// ---- Component: preview-pdf ----
|
|
2069
|
+
'core.component.preview-pdf.title': '查看文档',
|
|
2070
|
+
'core.component.preview-pdf.close': '关闭',
|
|
2071
|
+
'core.component.preview-pdf.pages-count': '{count} 页',
|
|
2072
|
+
'core.component.preview-pdf.tab.thumbnails': '页面',
|
|
2073
|
+
'core.component.preview-pdf.tab.outline': '目录',
|
|
2074
|
+
'core.component.preview-pdf.tab.search': '查找',
|
|
2075
|
+
'core.component.preview-pdf.first-page': '首页',
|
|
2076
|
+
'core.component.preview-pdf.prev-page': '上一页',
|
|
2077
|
+
'core.component.preview-pdf.next-page': '下一页',
|
|
2078
|
+
'core.component.preview-pdf.last-page': '末页',
|
|
2079
|
+
'core.component.preview-pdf.zoom-in': '放大',
|
|
2080
|
+
'core.component.preview-pdf.zoom-out': '缩小',
|
|
2081
|
+
'core.component.preview-pdf.fit-page': '适合页面',
|
|
2082
|
+
'core.component.preview-pdf.fit-width': '适合宽度',
|
|
2083
|
+
'core.component.preview-pdf.actual-size': '实际大小',
|
|
2084
|
+
'core.component.preview-pdf.rotate': '旋转',
|
|
2085
|
+
'core.component.preview-pdf.scroll-page': '单页',
|
|
2086
|
+
'core.component.preview-pdf.scroll-continuous': '连续滚动',
|
|
2087
|
+
'core.component.preview-pdf.print': '打印',
|
|
2088
|
+
'core.component.preview-pdf.download': '下载',
|
|
2089
|
+
'core.component.preview-pdf.fullscreen': '全屏',
|
|
2090
|
+
'core.component.preview-pdf.toggle-sidebar': '切换侧边栏',
|
|
2091
|
+
'core.component.preview-pdf.page-of': '第 {current} / {total} 页',
|
|
2092
|
+
'core.component.preview-pdf.empty.title': '没有文档',
|
|
2093
|
+
'core.component.preview-pdf.empty.subtitle': '尚无可显示的 PDF 文件',
|
|
2094
|
+
'core.component.preview-pdf.loading': '正在加载文档...',
|
|
2095
|
+
'core.component.preview-pdf.loading.page': '正在处理第 {current} / {total} 页',
|
|
2096
|
+
'core.component.preview-pdf.error.invalid.title': '无法加载文档',
|
|
2097
|
+
'core.component.preview-pdf.error.invalid.body': 'PDF 文件可能已损坏。请检查文件。',
|
|
2098
|
+
'core.component.preview-pdf.error.password.title': '受保护的文档',
|
|
2099
|
+
'core.component.preview-pdf.error.password.body': '此 PDF 文件需要密码才能打开。',
|
|
2100
|
+
'core.component.preview-pdf.error.network.title': '无法连接',
|
|
2101
|
+
'core.component.preview-pdf.error.network.body': '无法从服务器加载文件。请稍后再试。',
|
|
2102
|
+
'core.component.preview-pdf.error.unknown.title': '发生错误',
|
|
2103
|
+
'core.component.preview-pdf.error.unknown.body': '请重试或下载原始文件查看。',
|
|
2104
|
+
'core.component.preview-pdf.error.retry': '重试',
|
|
2105
|
+
'core.component.preview-pdf.error.download-raw': '下载原始文件',
|
|
2106
|
+
'core.component.preview-pdf.deferred.outline': '目录功能将在后续版本中添加。',
|
|
2107
|
+
'core.component.preview-pdf.deferred.search': '搜索功能将在后续版本中添加。',
|
|
2108
|
+
'core.component.preview-pdf.search': '搜索',
|
|
2109
|
+
'core.component.preview-pdf.search-placeholder': '在文档中搜索...',
|
|
2110
|
+
'core.component.preview-pdf.search-case': '区分大小写',
|
|
2111
|
+
'core.component.preview-pdf.search-whole': '全词匹配',
|
|
2112
|
+
'core.component.preview-pdf.search-no-results': '未找到结果',
|
|
2113
|
+
'core.component.preview-pdf.search-results-count': '关于 "{term}" 的 {count} 个结果',
|
|
2114
|
+
'core.component.preview-pdf.search-prev': '上一个结果',
|
|
2115
|
+
'core.component.preview-pdf.search-next': '下一个结果',
|
|
2116
|
+
'core.component.preview-pdf.search-close': '关闭搜索',
|
|
2117
|
+
// ---- Component: table ----
|
|
2118
|
+
'core.component.table.setup': '表格设置',
|
|
2119
|
+
'core.component.table.column-header': '列标题',
|
|
2120
|
+
'core.component.table.width': '宽度',
|
|
2121
|
+
'core.component.table.fixed': '固定',
|
|
2122
|
+
'core.component.table.char-limit': '字符限制',
|
|
2123
|
+
'core.component.table.skip': '跳过',
|
|
2124
|
+
'core.component.table.apply': '应用',
|
|
2125
|
+
'core.component.table.filter': '筛选',
|
|
2126
|
+
'core.component.table.clear-selection': '清除选择',
|
|
2127
|
+
'core.component.table.customize': '自定义',
|
|
2128
|
+
'core.component.table.search': '搜索',
|
|
2129
|
+
'core.component.table.reload': '刷新',
|
|
2130
|
+
'core.component.table.setup-short': '设置',
|
|
2131
|
+
'core.component.table.no-results': '未找到匹配结果',
|
|
2132
|
+
'core.component.table.no-results-hint': '请使用其他条件搜索或筛选',
|
|
2133
|
+
'core.component.table.choose-filter-hint': '请先选择筛选条件',
|
|
2134
|
+
'core.component.table.no-data': '暂无数据',
|
|
2135
|
+
'core.component.table.export-excel': '导出 Excel',
|
|
2136
|
+
'core.component.table.export-csv': '导出 CSV',
|
|
2137
|
+
'core.component.table.showing': '显示:',
|
|
2138
|
+
'core.component.table.paginator.first-page': '首页',
|
|
2139
|
+
'core.component.table.paginator.last-page': '末页',
|
|
2140
|
+
'core.component.table.paginator.items-per-page': '显示',
|
|
2141
|
+
'core.component.table.paginator.next-page': '下一页',
|
|
2142
|
+
'core.component.table.paginator.previous-page': '上一页',
|
|
2143
|
+
'core.component.table.error-occurred': '发生错误',
|
|
2144
|
+
'core.component.table.not-an-array': '数据不是数组',
|
|
2145
|
+
'core.component.table.config.confirm-reset': '确认将所有设置恢复为默认值',
|
|
2146
|
+
'core.component.table.popup-export.select-columns': '请选择要导出的列',
|
|
2147
|
+
'core.component.table.selector-action.default-msg': '项已选择',
|
|
2148
|
+
'core.component.tab-router.too-many-tabs': '您已打开过多标签页。',
|
|
2149
|
+
// ---- Component: upload-file ----
|
|
2150
|
+
'core.component.upload-file.upload': '上传文件',
|
|
2151
|
+
'core.component.upload-file.error-occurred': '发生错误',
|
|
2152
|
+
'core.component.upload-file.please-upload': '请上传文件/图片',
|
|
2153
|
+
'core.component.upload-file.desc-format-and-size': '格式: {exts},最大: {maxSize}MB',
|
|
2154
|
+
'core.component.upload-file.desc-format': '格式: {exts}',
|
|
2155
|
+
'core.component.upload-file.desc-max-size': '最大: {maxSize}MB',
|
|
2156
|
+
'core.component.upload-file.not-image': '[{name}] 上传的文件不是图片',
|
|
2157
|
+
'core.component.upload-file.invalid-format': '[{name}] 上传的文件格式不正确: {exts}',
|
|
2158
|
+
'core.component.upload-file.size-exceeded': '[{name}] 最大文件大小: {maxSize} MB',
|
|
2159
|
+
'core.component.upload-file.upload-failed': '文件上传过程中发生错误',
|
|
2160
|
+
'core.component.upload-file.too-many-files': '所选文件数量过多,请检查数量',
|
|
2161
|
+
'core.component.upload-file.confirm-delete-message': '是否要删除此文件?此操作无法撤销',
|
|
2162
|
+
'core.component.upload-file.confirm-delete-title': '确认删除?',
|
|
2163
|
+
'core.component.upload-file.confirm-yes': '确认',
|
|
2164
|
+
'core.component.upload-file.confirm-no': '取消',
|
|
2165
|
+
'core.component.upload-file.no-configuration': '请注入 SD_UPLOAD_FILE_CONFIGURATION 或将 [upload] 直接传入组件',
|
|
2166
|
+
'core.component.upload-file.no-configuration-key': '未找到 key=\'{key}\' 对应的上传配置。请检查 providers 或直接传入 [upload]',
|
|
2167
|
+
'core.component.upload-file.preview-title': '图片预览',
|
|
2168
|
+
// ---- Module: layout (sidebar / user menu) ----
|
|
2169
|
+
'core.module.layout.user.change-password': '修改密码',
|
|
2170
|
+
'core.module.layout.user.logout': '退出登录',
|
|
2171
|
+
'core.module.layout.sidebar.search': '搜索',
|
|
2172
|
+
// ---- Module: layout (greeting + weekday) ----
|
|
2173
|
+
'core.module.layout.greeting.hello': '你好,{name}',
|
|
2174
|
+
'core.module.layout.weekday.0': '星期日',
|
|
2175
|
+
'core.module.layout.weekday.1': '星期一',
|
|
2176
|
+
'core.module.layout.weekday.2': '星期二',
|
|
2177
|
+
'core.module.layout.weekday.3': '星期三',
|
|
2178
|
+
'core.module.layout.weekday.4': '星期四',
|
|
2179
|
+
'core.module.layout.weekday.5': '星期五',
|
|
2180
|
+
'core.module.layout.weekday.6': '星期六',
|
|
2181
|
+
'core.module.layout.today-info.format': '{weekday},{date}',
|
|
2182
|
+
// ---- Module: layout (forbidden page) ----
|
|
2183
|
+
'core.module.layout.forbidden.title': '禁止访问',
|
|
2184
|
+
'core.module.layout.forbidden.message': '您没有访问此页面的权限。请联系管理员或返回首页',
|
|
2185
|
+
'core.module.layout.forbidden.back-home': '返回首页',
|
|
2186
|
+
// ---- Module: layout (not-found page) ----
|
|
2187
|
+
'core.module.layout.not-found.title': '404 - 页面未找到',
|
|
2188
|
+
'core.module.layout.not-found.message': '您正在查找的页面不存在或已被移除。请检查 URL 或返回首页继续。',
|
|
2189
|
+
'core.module.layout.not-found.back': '返回',
|
|
2190
|
+
// ---- Module: layout (home page) ----
|
|
2191
|
+
'core.module.layout.home.tab-name': '首页',
|
|
2192
|
+
'core.module.layout.home.feature.data': '数据',
|
|
2193
|
+
'core.module.layout.home.feature.reports': '报表',
|
|
2194
|
+
'core.module.layout.home.feature.users': '用户',
|
|
2195
|
+
'core.module.layout.home.feature.workflow': '流程',
|
|
2196
|
+
'core.module.layout.home.feature.audit': '审计',
|
|
2197
|
+
'core.module.layout.home.feature.integration': '集成',
|
|
2198
|
+
// ---- Module: layout (mock fallback when SD_LAYOUT_CONFIGURATION is not provided) ----
|
|
2199
|
+
'core.module.layout.mock.user.full-name': '演示用户',
|
|
2200
|
+
// ---- Module: generic (generic-select) ----
|
|
2201
|
+
'core.module.generic.generic-select.detail-link': '详情',
|
|
2202
|
+
};
|
|
2203
|
+
|
|
2204
|
+
const I18N_MESSAGES = {
|
|
708
2205
|
vi: VI_MESSAGES,
|
|
709
2206
|
en: EN_MESSAGES,
|
|
2207
|
+
ja: JA_MESSAGES,
|
|
2208
|
+
ko: KO_MESSAGES,
|
|
2209
|
+
zh: ZH_MESSAGES,
|
|
710
2210
|
};
|
|
711
2211
|
|
|
712
|
-
class
|
|
2212
|
+
class I18nService {
|
|
713
2213
|
#config = inject(SD_CORE_CONFIGURATION, { optional: true });
|
|
2214
|
+
// Custom catalog (signal) — non-null khi user cấu hình `language: () => I18nCatalog`.
|
|
2215
|
+
// Khi non-null, `messages` computed sẽ ưu tiên trả về catalog này thay vì I18N_MESSAGES[lang].
|
|
2216
|
+
// PHẢI khai báo TRƯỚC `#language` vì `#resolveInitial()` chạy trong initializer của `#language`
|
|
2217
|
+
// và có thể gọi `this.#customMessages.set(...)` (sync custom catalog path).
|
|
2218
|
+
#customMessages = signal(null);
|
|
714
2219
|
#language = signal(this.#resolveInitial());
|
|
715
2220
|
#warned = new Set();
|
|
716
2221
|
language = this.#language.asReadonly();
|
|
717
|
-
messages = computed(() =>
|
|
718
|
-
|
|
719
|
-
if (
|
|
2222
|
+
messages = computed(() => {
|
|
2223
|
+
const custom = this.#customMessages();
|
|
2224
|
+
if (custom)
|
|
2225
|
+
return custom;
|
|
2226
|
+
return I18N_MESSAGES[this.#language()];
|
|
2227
|
+
});
|
|
2228
|
+
// Đổi ngôn ngữ require reload trang (model "reload trên đổi"). Pipe `translate` là pure
|
|
2229
|
+
// nên không tự cập nhật runtime — phải reload để cache pipe được rebuild với messages mới.
|
|
2230
|
+
// Test có thể pass `{ reload: false }` để tránh reload page trong Karma.
|
|
2231
|
+
setLanguage(lang, opts = { reload: true }) {
|
|
2232
|
+
if (!SUPPORTED_LANGUAGES.includes(lang))
|
|
720
2233
|
return;
|
|
721
|
-
this.#language
|
|
2234
|
+
if (this.#language() === lang && !this.#customMessages())
|
|
2235
|
+
return; // no-op if same and not in custom mode
|
|
2236
|
+
// User chọn 'vi'/'en' rõ ràng -> clear custom mode (override custom provider)
|
|
2237
|
+
this.#customMessages.set(null);
|
|
722
2238
|
try {
|
|
723
|
-
localStorage.setItem(
|
|
2239
|
+
localStorage.setItem(I18N_STORAGE_KEY, lang);
|
|
724
2240
|
}
|
|
725
2241
|
catch { /* ignore */ }
|
|
2242
|
+
this.#language.set(lang);
|
|
2243
|
+
if (opts.reload && typeof window !== 'undefined') {
|
|
2244
|
+
window.location.reload();
|
|
2245
|
+
}
|
|
726
2246
|
}
|
|
727
2247
|
t(key, params) {
|
|
728
|
-
|
|
729
|
-
const raw =
|
|
2248
|
+
// Đọc từ computed `messages()` để hỗ trợ cả custom catalog lẫn built-in lang.
|
|
2249
|
+
const raw = this.messages()[key] ?? this.#fallback(key);
|
|
730
2250
|
return this.#interpolate(raw, params);
|
|
731
2251
|
}
|
|
732
2252
|
#fallback(key) {
|
|
733
|
-
const vi =
|
|
2253
|
+
const vi = I18N_MESSAGES.vi[key];
|
|
734
2254
|
if (vi !== undefined) {
|
|
735
|
-
this.#warnOnce(`[
|
|
2255
|
+
this.#warnOnce(`[I18n] Missing key in ${this.#language()}: ${key} (fallback to vi)`);
|
|
736
2256
|
return vi;
|
|
737
2257
|
}
|
|
738
|
-
this.#warnOnce(`[
|
|
2258
|
+
this.#warnOnce(`[I18n] Missing key: ${key}`);
|
|
739
2259
|
return key;
|
|
740
2260
|
}
|
|
741
2261
|
#interpolate(raw, params) {
|
|
@@ -750,41 +2270,58 @@ class SdI18nService {
|
|
|
750
2270
|
console.warn(msg);
|
|
751
2271
|
}
|
|
752
2272
|
#resolveInitial() {
|
|
2273
|
+
// 1) localStorage (only 'vi'/'en' supported there) — luôn ưu tiên cao nhất
|
|
753
2274
|
try {
|
|
754
|
-
const stored = localStorage.getItem(
|
|
755
|
-
if (stored &&
|
|
2275
|
+
const stored = localStorage.getItem(I18N_STORAGE_KEY);
|
|
2276
|
+
if (stored && SUPPORTED_LANGUAGES.includes(stored))
|
|
756
2277
|
return stored;
|
|
757
2278
|
}
|
|
758
2279
|
catch { /* ignore */ }
|
|
759
2280
|
const configured = this.#config?.language;
|
|
760
|
-
|
|
2281
|
+
// 2) function — custom language provider (sync only)
|
|
2282
|
+
if (typeof configured === 'function') {
|
|
2283
|
+
this.#loadCustom(configured);
|
|
2284
|
+
return 'vi'; // language() vẫn báo 'vi' trong custom mode; messages() ưu tiên #customMessages
|
|
2285
|
+
}
|
|
2286
|
+
// 3) string — built-in lang
|
|
2287
|
+
if (configured && SUPPORTED_LANGUAGES.includes(configured))
|
|
761
2288
|
return configured;
|
|
2289
|
+
// 4) default
|
|
762
2290
|
return 'vi';
|
|
763
2291
|
}
|
|
764
|
-
|
|
765
|
-
|
|
2292
|
+
#loadCustom(fn) {
|
|
2293
|
+
try {
|
|
2294
|
+
const catalog = fn();
|
|
2295
|
+
this.#customMessages.set(catalog);
|
|
2296
|
+
}
|
|
2297
|
+
catch (err) {
|
|
2298
|
+
console.warn('[I18n] Custom language fn threw:', err);
|
|
2299
|
+
}
|
|
2300
|
+
}
|
|
2301
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type: I18nService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
2302
|
+
static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type: I18nService, providedIn: 'root' });
|
|
766
2303
|
}
|
|
767
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type:
|
|
2304
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type: I18nService, decorators: [{
|
|
768
2305
|
type: Injectable,
|
|
769
2306
|
args: [{ providedIn: 'root' }]
|
|
770
2307
|
}] });
|
|
771
2308
|
|
|
772
|
-
class
|
|
773
|
-
#i18n = inject(
|
|
2309
|
+
class TranslatePipe {
|
|
2310
|
+
#i18n = inject(I18nService);
|
|
774
2311
|
transform(key, params) {
|
|
775
2312
|
return this.#i18n.t(key, params);
|
|
776
2313
|
}
|
|
777
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type:
|
|
778
|
-
static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "19.2.21", ngImport: i0, type:
|
|
2314
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type: TranslatePipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
|
|
2315
|
+
static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "19.2.21", ngImport: i0, type: TranslatePipe, isStandalone: true, name: "translate" });
|
|
779
2316
|
}
|
|
780
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type:
|
|
2317
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.21", ngImport: i0, type: TranslatePipe, decorators: [{
|
|
781
2318
|
type: Pipe,
|
|
782
|
-
args: [{ name: '
|
|
2319
|
+
args: [{ name: 'translate', standalone: true }]
|
|
783
2320
|
}] });
|
|
784
2321
|
|
|
785
2322
|
/**
|
|
786
2323
|
* Generated bundle index. Do not edit.
|
|
787
2324
|
*/
|
|
788
2325
|
|
|
789
|
-
export {
|
|
2326
|
+
export { I18N_MESSAGES, I18N_STORAGE_KEY, I18nService, TranslatePipe };
|
|
790
2327
|
//# sourceMappingURL=sd-angular-core-i18n.mjs.map
|