дзеркало
https://github.com/l0ng-ai/openidea.git
синхронізовано 2026-11-09 11:15:40 +02:00
fix(i18n): Translate the remaining UI text (Git, hierarchy, pull requests, dialogs, aria labels) (#114)
Hard-coded UI text, titles and aria-labels in about 110 components (Git panels, hierarchy, pull requests, dialogs, settings, welcome) now go through tx; spliced fragments became whole sentences (fileCount, noneFoundLabel, hierarchyTitle) and pull request states use keyed messages. 225 zh entries added, stale fragment entries removed.
Also: tx used as a tag without interpolations (tx`No checks`) now looks the text up exactly instead of as a template, so it is translated like tx("No checks"); the text-catalog test checks such tags as plain literals. Check and test counts reuse the existing "{count} passed" / "{failed} failing" entries.
Claude-Session: https://claude.ai/code/session_01VUYsdXA2nkF5v6zsC93dpn
Co-authored-by: jaw52 <[email protected]>
Цей коміт міститься в:
121 files changed
+854
-457
No files matched your search
@@ -19,9 +19,11 @@ import { openLocation } from "./ipc";
|
||||
import {
|
||||
ROOT_ID,
|
||||
directionLabel,
|
||||
hierarchyTitle,
|
||||
hierarchyTarget,
|
||||
loadChildren,
|
||||
refreshHierarchy,
|
||||
noneFoundLabel,
|
||||
setDirection,
|
||||
useHierarchy,
|
||||
type HierarchyNode,
|
||||
@@ -56,7 +58,7 @@ export function HierarchyTabs() {
|
||||
const direction = useHierarchy((s) => s.direction);
|
||||
const root = useHierarchy((s) => s.root);
|
||||
if (!root) return null;
|
||||
const label = `${directionLabel(mode, direction)} of ${root.name}`;
|
||||
const label = hierarchyTitle(mode, direction, root.name);
|
||||
return (
|
||||
<Tabs
|
||||
variant="compact"
|
||||
@@ -74,7 +76,7 @@ function HierarchyToolbar() {
|
||||
const direction = useHierarchy((s) => s.direction);
|
||||
const autoscroll = useHierarchyOptions((s) => s.autoscroll);
|
||||
return (
|
||||
<div className={styles.toolbar} role="toolbar" aria-label="Hierarchy actions">
|
||||
<div className={styles.toolbar} role="toolbar" aria-label={tx("Hierarchy actions")}>
|
||||
<IconButton
|
||||
icon="arrow-up"
|
||||
size="small"
|
||||
@@ -165,7 +167,7 @@ export function HierarchyView() {
|
||||
</span>
|
||||
)}
|
||||
{!loading && !failed.has(ROOT_ID) && children.get(ROOT_ID)?.length === 0 && (
|
||||
<span className={styles.muted}>— no {directionLabel(mode, direction).toLowerCase()} found</span>
|
||||
<span className={styles.muted}>{noneFoundLabel(mode, direction)}</span>
|
||||
)}
|
||||
</span>
|
||||
);
|
||||
@@ -180,7 +182,7 @@ export function HierarchyView() {
|
||||
<span className={styles.muted}>
|
||||
{basename(item.path)}:{item.selectionRange.start.line + 1}
|
||||
</span>
|
||||
{calls > 1 && <span className={styles.muted}>({calls} calls)</span>}
|
||||
{calls > 1 && <span className={styles.muted}>{tx`(${calls} calls)`}</span>}
|
||||
{failed.has(n.id) && (
|
||||
<span className={styles.error}>
|
||||
<T>failed to load</T>
|
||||
|
||||
@@ -16,6 +16,7 @@ import { openLocation, readFileLines } from "./ipc";
|
||||
import { showUsageResults, usageCount, useUsagesPopup, type Usage, type UsageGroup } from "./usages";
|
||||
import { UsagePreview } from "./UsagesView";
|
||||
import styles from "./UsagesPopup.module.css";
|
||||
import { tx } from "@/platform/i18n";
|
||||
|
||||
const close = () => useUsagesPopup.setState({ open: false });
|
||||
|
||||
@@ -118,8 +119,8 @@ function UsagesPopupInner() {
|
||||
<div className={styles.focus} tabIndex={0} data-autofocus onKeyDown={onKeyDown}>
|
||||
<div className={styles.header}>
|
||||
<span className={styles.title}>
|
||||
Usages{symbol ? ` of ${symbol}` : ""}{" "}
|
||||
<span className={styles.count}>{filter ? `${items.length} of ${total}` : total} found</span>
|
||||
{symbol ? tx`Usages of ${symbol}` : tx("Usages")}{" "}
|
||||
<span className={styles.count}>{filter ? tx`${items.length} of ${total} found` : tx`${total} found`}</span>
|
||||
</span>
|
||||
{filter && (
|
||||
<span className={clsx(styles.filter, !items.length && styles.noMatch)} role="status">
|
||||
@@ -135,7 +136,8 @@ function UsagesPopupInner() {
|
||||
onClick={() => setUsagesPopupPreview(!preview)}
|
||||
/>
|
||||
<button type="button" className={styles.link} onClick={openInFindWindow}>
|
||||
Open in Find Window{keys ? ` ${keys}` : ""}
|
||||
{tx("Open in Find Window")}
|
||||
{keys ? ` ${keys}` : ""}
|
||||
</button>
|
||||
</div>
|
||||
{note && <div className={styles.note}>{note}</div>}
|
||||
@@ -150,7 +152,7 @@ function UsagesPopupInner() {
|
||||
rowHeight={ROW}
|
||||
aria-label="Usages"
|
||||
onActivate={pick}
|
||||
empty={<div className={styles.empty}>Nothing matches '{filter}'</div>}
|
||||
empty={<div className={styles.empty}>{tx`Nothing matches '${filter}'`}</div>}
|
||||
renderItem={(u) => (
|
||||
<div className={styles.row}>
|
||||
<Icon name={fileIconName(basename(u.path))} size={14} className={styles.icon} />
|
||||
@@ -234,7 +236,7 @@ function UsageCodePreview({ usage }: { usage: Usage | null }) {
|
||||
}, [usage, loaded]);
|
||||
|
||||
return (
|
||||
<div className={styles.preview} role="region" aria-label="Preview">
|
||||
<div className={styles.preview} role="region" aria-label={tx("Preview")}>
|
||||
<div ref={host} className={clsx(styles.previewEditor, loaded !== path && styles.previewHidden)} />
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -5,6 +5,7 @@ import { IpcError, call, commands } from "@/platform/ipc";
|
||||
import { toolWindowService } from "@/workbench/contributions";
|
||||
import { basename } from "@/platform/project";
|
||||
import { caretContext, hint, lspRequest, reportError, withDocument, type CaretContext } from "./ipc";
|
||||
import { tx } from "@/platform/i18n";
|
||||
|
||||
export type HierarchyMode = "call" | "type";
|
||||
|
||||
@@ -56,9 +57,21 @@ export function resetHierarchy() {
|
||||
}));
|
||||
}
|
||||
|
||||
/** The empty-result line of the hierarchy tree. */
|
||||
export function noneFoundLabel(mode: HierarchyMode, direction: HierarchyDirection): string {
|
||||
if (mode === "call") return direction === "incoming" ? tx`— no callers found` : tx`— no callees found`;
|
||||
return direction === "incoming" ? tx`— no supertypes found` : tx`— no subtypes found`;
|
||||
}
|
||||
|
||||
export function directionLabel(mode: HierarchyMode, direction: HierarchyDirection): string {
|
||||
if (mode === "call") return direction === "incoming" ? "Callers" : "Callees";
|
||||
return direction === "incoming" ? "Supertypes" : "Subtypes";
|
||||
if (mode === "call") return direction === "incoming" ? tx("Callers") : tx("Callees");
|
||||
return direction === "incoming" ? tx("Supertypes") : tx("Subtypes");
|
||||
}
|
||||
|
||||
/** The tab title of the hierarchy tree, e.g. "Callers of main". */
|
||||
export function hierarchyTitle(mode: HierarchyMode, direction: HierarchyDirection, name: string): string {
|
||||
if (mode === "call") return direction === "incoming" ? tx`Callers of ${name}` : tx`Callees of ${name}`;
|
||||
return direction === "incoming" ? tx`Supertypes of ${name}` : tx`Subtypes of ${name}`;
|
||||
}
|
||||
|
||||
function request(mode: HierarchyMode, doc: number, line: number, col: number, direction: HierarchyDirection) {
|
||||
|
||||
Reference in new issue
Заблокувати користувача