Add Hebrew translation and RTL support via Docker injection
Injects custom CSS and JS into the Paperclip UI during Docker build: - RTL layout overrides for Tailwind, Radix UI, and MDXEditor - Hebrew translation script with MutationObserver for dynamic content - Patch script to modify index.html with dir="rtl" and lang="he" Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -4,6 +4,12 @@ RUN apt-get update && apt-get install -y --no-install-recommends curl && rm -rf
|
|||||||
|
|
||||||
RUN npm install -g paperclipai
|
RUN npm install -g paperclipai
|
||||||
|
|
||||||
|
# Inject Hebrew RTL + translation into the UI
|
||||||
|
COPY assets/rtl-override.css /tmp/rtl-override.css
|
||||||
|
COPY assets/translate-he.js /tmp/translate-he.js
|
||||||
|
COPY patch-html.sh /tmp/patch-html.sh
|
||||||
|
RUN bash /tmp/patch-html.sh && rm -f /tmp/patch-html.sh /tmp/rtl-override.css /tmp/translate-he.js
|
||||||
|
|
||||||
RUN mkdir -p /data/instances/default/data/storage \
|
RUN mkdir -p /data/instances/default/data/storage \
|
||||||
/data/instances/default/data/backups \
|
/data/instances/default/data/backups \
|
||||||
/data/instances/default/secrets \
|
/data/instances/default/secrets \
|
||||||
|
|||||||
741
assets/rtl-override.css
Normal file
741
assets/rtl-override.css
Normal file
@@ -0,0 +1,741 @@
|
|||||||
|
/* ==========================================================================
|
||||||
|
Paperclip AI - RTL Override for Hebrew (dir="rtl")
|
||||||
|
Generated from analysis of index-CYurTMty.css (Tailwind v4.1.18 + MDXEditor)
|
||||||
|
|
||||||
|
Scoped under html[dir="rtl"] to apply only in RTL mode.
|
||||||
|
========================================================================== */
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
1. GLOBAL DIRECTION
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] {
|
||||||
|
direction: rtl;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] body {
|
||||||
|
text-align: right;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
2. TAILWIND UTILITY CLASSES - Padding Left/Right Swap
|
||||||
|
|
||||||
|
.pl-* -> padding-right, .pr-* -> padding-left
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .pl-1 { padding-left: 0; padding-right: calc(var(--spacing) * 1); }
|
||||||
|
html[dir="rtl"] .pl-2 { padding-left: 0; padding-right: calc(var(--spacing) * 2); }
|
||||||
|
html[dir="rtl"] .pl-3 { padding-left: 0; padding-right: calc(var(--spacing) * 3); }
|
||||||
|
html[dir="rtl"] .pl-4 { padding-left: 0; padding-right: calc(var(--spacing) * 4); }
|
||||||
|
html[dir="rtl"] .pl-5 { padding-left: 0; padding-right: calc(var(--spacing) * 5); }
|
||||||
|
html[dir="rtl"] .pl-5\.5 { padding-left: 0; padding-right: calc(var(--spacing) * 5.5); }
|
||||||
|
html[dir="rtl"] .pl-6 { padding-left: 0; padding-right: calc(var(--spacing) * 6); }
|
||||||
|
html[dir="rtl"] .pl-7 { padding-left: 0; padding-right: calc(var(--spacing) * 7); }
|
||||||
|
html[dir="rtl"] .pl-8 { padding-left: 0; padding-right: calc(var(--spacing) * 8); }
|
||||||
|
|
||||||
|
html[dir="rtl"] .pr-1 { padding-right: 0; padding-left: calc(var(--spacing) * 1); }
|
||||||
|
html[dir="rtl"] .pr-2 { padding-right: 0; padding-left: calc(var(--spacing) * 2); }
|
||||||
|
html[dir="rtl"] .pr-3 { padding-right: 0; padding-left: calc(var(--spacing) * 3); }
|
||||||
|
html[dir="rtl"] .pr-6 { padding-right: 0; padding-left: calc(var(--spacing) * 6); }
|
||||||
|
html[dir="rtl"] .pr-8 { padding-right: 0; padding-left: calc(var(--spacing) * 8); }
|
||||||
|
html[dir="rtl"] .pr-10 { padding-right: 0; padding-left: calc(var(--spacing) * 10); }
|
||||||
|
|
||||||
|
/* data-inset padding override */
|
||||||
|
html[dir="rtl"] .data-\[inset\]\:pl-8[data-inset] {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: calc(var(--spacing) * 8);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Responsive padding overrides */
|
||||||
|
html[dir="rtl"] .sm\:pl-1 { padding-left: 0; padding-right: calc(var(--spacing) * 1); }
|
||||||
|
html[dir="rtl"] .sm\:pr-3 { padding-right: 0; padding-left: calc(var(--spacing) * 3); }
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
3. TAILWIND UTILITY CLASSES - Margin Left/Right Swap
|
||||||
|
|
||||||
|
.ml-* -> margin-right, .mr-* -> margin-left
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .-ml-1\.5 { margin-left: 0; margin-right: calc(var(--spacing) * -1.5); }
|
||||||
|
html[dir="rtl"] .ml-0\.5 { margin-left: 0; margin-right: calc(var(--spacing) * 0.5); }
|
||||||
|
html[dir="rtl"] .ml-1 { margin-left: 0; margin-right: calc(var(--spacing) * 1); }
|
||||||
|
html[dir="rtl"] .ml-1\.5 { margin-left: 0; margin-right: calc(var(--spacing) * 1.5); }
|
||||||
|
html[dir="rtl"] .ml-2 { margin-left: 0; margin-right: calc(var(--spacing) * 2); }
|
||||||
|
html[dir="rtl"] .ml-3 { margin-left: 0; margin-right: calc(var(--spacing) * 3); }
|
||||||
|
html[dir="rtl"] .ml-4 { margin-left: 0; margin-right: calc(var(--spacing) * 4); }
|
||||||
|
html[dir="rtl"] .ml-5 { margin-left: 0; margin-right: calc(var(--spacing) * 5); }
|
||||||
|
html[dir="rtl"] .ml-auto { margin-left: 0; margin-right: auto; }
|
||||||
|
|
||||||
|
html[dir="rtl"] .mr-1 { margin-right: 0; margin-left: calc(var(--spacing) * 1); }
|
||||||
|
html[dir="rtl"] .mr-1\.5 { margin-right: 0; margin-left: calc(var(--spacing) * 1.5); }
|
||||||
|
html[dir="rtl"] .mr-2 { margin-right: 0; margin-left: calc(var(--spacing) * 2); }
|
||||||
|
html[dir="rtl"] .mr-auto { margin-right: 0; margin-left: auto; }
|
||||||
|
|
||||||
|
/* file selector button margin */
|
||||||
|
html[dir="rtl"] .file\:mr-4::file-selector-button {
|
||||||
|
margin-right: 0;
|
||||||
|
margin-left: calc(var(--spacing) * 4);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Responsive margin overrides */
|
||||||
|
html[dir="rtl"] .sm\:mr-1 { margin-right: 0; margin-left: calc(var(--spacing) * 1); }
|
||||||
|
html[dir="rtl"] .md\:ml-auto { margin-left: 0; margin-right: auto; }
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
4. TAILWIND UTILITY CLASSES - Left/Right Position Swap
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .left-0 { left: auto; right: calc(var(--spacing) * 0); }
|
||||||
|
html[dir="rtl"] .left-1\/2 { left: auto; right: 50%; }
|
||||||
|
html[dir="rtl"] .left-2 { left: auto; right: calc(var(--spacing) * 2); }
|
||||||
|
html[dir="rtl"] .left-2\.5 { left: auto; right: calc(var(--spacing) * 2.5); }
|
||||||
|
html[dir="rtl"] .left-3 { left: auto; right: calc(var(--spacing) * 3); }
|
||||||
|
html[dir="rtl"] .left-4 { left: auto; right: calc(var(--spacing) * 4); }
|
||||||
|
html[dir="rtl"] .left-\[-14px\] { left: auto; right: -14px; }
|
||||||
|
html[dir="rtl"] .left-\[50\%\] { left: auto; right: 50%; }
|
||||||
|
|
||||||
|
html[dir="rtl"] .-right-0\.5 { right: auto; left: calc(var(--spacing) * -0.5); }
|
||||||
|
html[dir="rtl"] .-right-2 { right: auto; left: calc(var(--spacing) * -2); }
|
||||||
|
html[dir="rtl"] .right-0 { right: auto; left: calc(var(--spacing) * 0); }
|
||||||
|
html[dir="rtl"] .right-1\.5 { right: auto; left: calc(var(--spacing) * 1.5); }
|
||||||
|
html[dir="rtl"] .right-2 { right: auto; left: calc(var(--spacing) * 2); }
|
||||||
|
html[dir="rtl"] .right-3 { right: auto; left: calc(var(--spacing) * 3); }
|
||||||
|
html[dir="rtl"] .right-4 { right: auto; left: calc(var(--spacing) * 4); }
|
||||||
|
html[dir="rtl"] .right-6 { right: auto; left: calc(var(--spacing) * 6); }
|
||||||
|
|
||||||
|
/* Responsive left positioning */
|
||||||
|
html[dir="rtl"] .sm\:left-3 { left: auto; right: calc(var(--spacing) * 3); }
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
5. TAILWIND UTILITY CLASSES - Text Align Swap
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .text-left { text-align: right; }
|
||||||
|
html[dir="rtl"] .text-right { text-align: left; }
|
||||||
|
html[dir="rtl"] .sm\:text-left { text-align: right; }
|
||||||
|
html[dir="rtl"] .sm\:text-right { text-align: left; }
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
6. TAILWIND UTILITY CLASSES - Float Swap
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .float-right { float: left; }
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
7. TAILWIND UTILITY CLASSES - Border Left/Right Swap
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .border-l {
|
||||||
|
border-left-style: none;
|
||||||
|
border-left-width: 0;
|
||||||
|
border-right-style: var(--tw-border-style);
|
||||||
|
border-right-width: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .border-l-2 {
|
||||||
|
border-left-style: none;
|
||||||
|
border-left-width: 0;
|
||||||
|
border-right-style: var(--tw-border-style);
|
||||||
|
border-right-width: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .border-l-transparent {
|
||||||
|
border-left-color: initial;
|
||||||
|
border-right-color: #0000;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .border-r {
|
||||||
|
border-right-style: none;
|
||||||
|
border-right-width: 0;
|
||||||
|
border-left-style: var(--tw-border-style);
|
||||||
|
border-left-width: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Responsive border overrides */
|
||||||
|
html[dir="rtl"] .sm\:border-l {
|
||||||
|
border-left-style: none;
|
||||||
|
border-left-width: 0;
|
||||||
|
border-right-style: var(--tw-border-style);
|
||||||
|
border-right-width: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .lg\:border-r {
|
||||||
|
border-right-style: none;
|
||||||
|
border-right-width: 0;
|
||||||
|
border-left-style: var(--tw-border-style);
|
||||||
|
border-left-width: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
8. TAILWIND UTILITY CLASSES - Rounded Left/Right Swap
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .rounded-l-md {
|
||||||
|
border-top-left-radius: 0;
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-top-right-radius: .5rem;
|
||||||
|
border-bottom-right-radius: .5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .rounded-r-md {
|
||||||
|
border-top-right-radius: 0;
|
||||||
|
border-bottom-right-radius: 0;
|
||||||
|
border-top-left-radius: .5rem;
|
||||||
|
border-bottom-left-radius: .5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .rounded-r-full {
|
||||||
|
border-top-right-radius: 0;
|
||||||
|
border-bottom-right-radius: 0;
|
||||||
|
border-top-left-radius: 3.40282e38px;
|
||||||
|
border-bottom-left-radius: 3.40282e38px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
9. TAILWIND UTILITY CLASSES - TranslateX Flip
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .-translate-x-1\/2 { --tw-translate-x: 50%; }
|
||||||
|
html[dir="rtl"] .-translate-x-4 { --tw-translate-x: calc(var(--spacing) * 4); }
|
||||||
|
html[dir="rtl"] .-translate-x-full { --tw-translate-x: 100%; }
|
||||||
|
html[dir="rtl"] .translate-x-0 { --tw-translate-x: calc(var(--spacing) * 0); }
|
||||||
|
html[dir="rtl"] .translate-x-0\.5 { --tw-translate-x: calc(var(--spacing) * -0.5); }
|
||||||
|
html[dir="rtl"] .translate-x-4\.5 { --tw-translate-x: calc(var(--spacing) * -4.5); }
|
||||||
|
html[dir="rtl"] .translate-x-5 { --tw-translate-x: calc(var(--spacing) * -5); }
|
||||||
|
html[dir="rtl"] .translate-x-\[-50\%\] { --tw-translate-x: 50%; }
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
10. RADIX UI - data-side tooltip/popover offset swap
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .data-\[side\=left\]\:-translate-x-1[data-side=left] {
|
||||||
|
--tw-translate-x: calc(var(--spacing) * 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .data-\[side\=right\]\:translate-x-1[data-side=right] {
|
||||||
|
--tw-translate-x: calc(var(--spacing) * -1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
11. MDXEditor - Toolbar Components
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
/* Toolbar root - sticky, scrollable row */
|
||||||
|
html[dir="rtl"] [class*="_toolbarRoot_"] {
|
||||||
|
flex-direction: row-reverse;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Toolbar mode switch - push to left in RTL (was margin-left:auto) */
|
||||||
|
html[dir="rtl"] [class*="_toolbarModeSwitch_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Toolbar separator - swap border sides */
|
||||||
|
html[dir="rtl"] [class*="_toolbarRoot_"] div[role="separator"] {
|
||||||
|
border-left: 1px solid var(--baseBase);
|
||||||
|
border-right: 1px solid var(--baseBorder);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Toolbar button adjacency spacing */
|
||||||
|
html[dir="rtl"] [class*="_toolbarButton_"] + [class*="_toolbarButton_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: var(--spacing-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Toolbar toggle first/last child border-radius swap */
|
||||||
|
html[dir="rtl"] [class*="_toolbarToggleSingleGroup_"]:first-of-type [class*="_toolbarToggleItem_"]:only-child,
|
||||||
|
html[dir="rtl"] [class*="_toolbarToggleSingleGroup_"]:only-child [class*="_toolbarToggleItem_"]:first-child,
|
||||||
|
html[dir="rtl"] [class*="_toolbarModeSwitch_"] [class*="_toolbarToggleItem_"]:first-child {
|
||||||
|
border-top-left-radius: 0;
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-top-right-radius: var(--radius-base);
|
||||||
|
border-bottom-right-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_toolbarToggleSingleGroup_"]:last-of-type [class*="_toolbarToggleItem_"]:only-child,
|
||||||
|
html[dir="rtl"] [class*="_toolbarToggleSingleGroup_"]:only-child [class*="_toolbarToggleItem_"]:last-child,
|
||||||
|
html[dir="rtl"] [class*="_toolbarModeSwitch_"] [class*="_toolbarToggleItem_"]:last-child {
|
||||||
|
border-top-right-radius: 0;
|
||||||
|
border-bottom-right-radius: 0;
|
||||||
|
border-top-left-radius: var(--radius-base);
|
||||||
|
border-bottom-left-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Dropdown arrow - push to right in RTL (was margin-left:auto) */
|
||||||
|
html[dir="rtl"] [class*="_toolbarNodeKindSelectDropdownArrow_"],
|
||||||
|
html[dir="rtl"] [class*="_selectDropdownArrow_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Dropdown container - border radius swap */
|
||||||
|
html[dir="rtl"] [class*="_toolbarNodeKindSelectContainer_"],
|
||||||
|
html[dir="rtl"] [class*="_toolbarButtonDropdownContainer_"],
|
||||||
|
html[dir="rtl"] [class*="_toolbarCodeBlockLanguageSelectContent_"],
|
||||||
|
html[dir="rtl"] [class*="_selectContainer_"] {
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-bottom-right-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_toolbarButtonDropdownContainer_"],
|
||||||
|
html[dir="rtl"] [class*="_toolbarButtonDropdownContainer_"] [class*="_selectItem_"]:first-child {
|
||||||
|
border-top-right-radius: 0;
|
||||||
|
border-top-left-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Select trigger open state - radius swap */
|
||||||
|
html[dir="rtl"] [class*="_toolbarNodeKindSelectTrigger_"][data-state="open"],
|
||||||
|
html[dir="rtl"] [class*="_toolbarButtonSelectTrigger_"][data-state="open"],
|
||||||
|
html[dir="rtl"] [class*="_selectTrigger_"][data-state="open"] {
|
||||||
|
border-bottom-right-radius: var(--radius-none);
|
||||||
|
border-bottom-left-radius: var(--radius-none);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Select item last child - radius swap */
|
||||||
|
html[dir="rtl"] [class*="_toolbarNodeKindSelectItem_"]:last-child,
|
||||||
|
html[dir="rtl"] [class*="_selectItem_"]:last-child {
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-bottom-right-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
12. MDXEditor - CodeMirror & Image Edit Toolbars
|
||||||
|
Position: was right:0 -> left:0, border-bottom-left -> border-bottom-right
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_codeMirrorToolbar_"] {
|
||||||
|
right: auto;
|
||||||
|
left: 0;
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-bottom-right-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_editImageToolbar_"] {
|
||||||
|
right: auto;
|
||||||
|
left: 0;
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-bottom-right-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
13. MDXEditor - Property Panel
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_propertyPanelTitle_"] {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_propertyEditorTable_"] th {
|
||||||
|
text-align: right;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_propertyEditorTable_"] [class*="_readOnlyColumnCell_"] {
|
||||||
|
padding-left: initial;
|
||||||
|
padding-right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_readOnlyColumnCell_"] {
|
||||||
|
padding-left: initial;
|
||||||
|
padding-right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_propertyEditorTable_"] td:last-child [class*="_iconButton_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: var(--spacing-4);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
14. MDXEditor - Dialog
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
/* Dialog centered positioning - no swap needed (translate-50% centers) */
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_dialogTitle_"] {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Link dialog input button */
|
||||||
|
html[dir="rtl"] [class*="_linkDialogInputWrapper_"] > button {
|
||||||
|
padding-right: 0;
|
||||||
|
padding-left: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Link dialog input dropdown open state */
|
||||||
|
html[dir="rtl"] [class*="_linkDialogInputWrapper_"][data-visible-dropdown="true"] {
|
||||||
|
border-bottom-left-radius: var(--radius-none);
|
||||||
|
border-bottom-right-radius: var(--radius-none);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Link dialog preview anchor */
|
||||||
|
html[dir="rtl"] [class*="_linkDialogPreviewAnchor_"] {
|
||||||
|
margin-right: 0;
|
||||||
|
margin-left: var(--spacing-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
15. MDXEditor - Generic Component Name
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_genericComponentName_"] {
|
||||||
|
padding-right: 0;
|
||||||
|
padding-left: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
16. MDXEditor - Table Editor
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_tableEditor_"] thead > tr > th {
|
||||||
|
text-align: left; /* was right, swap */
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_toolCell_"] {
|
||||||
|
text-align: left; /* was right, swap */
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_leftAlignedCell_"] {
|
||||||
|
text-align: right; /* was left, swap */
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_rightAlignedCell_"] {
|
||||||
|
text-align: left; /* was right, swap */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Table column editor toolbar separators */
|
||||||
|
html[dir="rtl"] [class*="_tableColumnEditorToolbar_"] [role="separator"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: var(--spacing-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Add column button - was on right side */
|
||||||
|
html[dir="rtl"] [class*="_addColumnButton_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: var(--spacing-px);
|
||||||
|
border-top-right-radius: 0;
|
||||||
|
border-bottom-right-radius: 0;
|
||||||
|
border-top-left-radius: var(--radius-medium);
|
||||||
|
border-bottom-left-radius: var(--radius-medium);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Toggle group first/last child radius swap */
|
||||||
|
html[dir="rtl"] [class*="_toggleGroupRoot_"] button:first-child {
|
||||||
|
border-top-left-radius: 0;
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-top-right-radius: var(--radius-base);
|
||||||
|
border-bottom-right-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_toggleGroupRoot_"] button:last-child {
|
||||||
|
border-top-right-radius: 0;
|
||||||
|
border-bottom-right-radius: 0;
|
||||||
|
border-top-left-radius: var(--radius-base);
|
||||||
|
border-bottom-left-radius: var(--radius-base);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
17. MDXEditor - Diff Source Toggle
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_diffSourceToggleWrapper_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: auto;
|
||||||
|
right: auto;
|
||||||
|
left: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
18. MDXEditor - Select with Label
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_selectWithLabel_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_toolbarTitleMode_"] {
|
||||||
|
margin-left: 0;
|
||||||
|
margin-right: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
19. MDXEditor - Downshift Autocomplete
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_downshiftInputWrapper_"] > button {
|
||||||
|
padding-right: 0;
|
||||||
|
padding-left: var(--spacing-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_downshiftInputWrapper_"][data-visible-dropdown="true"] {
|
||||||
|
border-bottom-left-radius: var(--radius-none);
|
||||||
|
border-bottom-right-radius: var(--radius-none);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_downshiftAutocompleteContainer_"] ul {
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-bottom-right-radius: var(--radius-medium);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_downshiftAutocompleteContainer_"] ul li:last-of-type {
|
||||||
|
border-bottom-left-radius: 0;
|
||||||
|
border-bottom-right-radius: var(--radius-medium);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
20. MDXEditor - List Items (Checkbox)
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_listItemChecked_"],
|
||||||
|
html[dir="rtl"] [class*="_listItemUnchecked_"] {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: var(--spacing-6);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_listItemChecked_"]:before,
|
||||||
|
html[dir="rtl"] [class*="_listItemUnchecked_"]:before {
|
||||||
|
left: auto;
|
||||||
|
right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_listItemChecked_"]:after {
|
||||||
|
left: auto;
|
||||||
|
right: var(--spacing-1_5);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
21. MDXEditor - Admonitions (Info/Warning/Danger blocks)
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_admonitionDanger_"],
|
||||||
|
html[dir="rtl"] [class*="_admonitionInfo_"],
|
||||||
|
html[dir="rtl"] [class*="_admonitionNote_"],
|
||||||
|
html[dir="rtl"] [class*="_admonitionTip_"],
|
||||||
|
html[dir="rtl"] [class*="_admonitionCaution_"] {
|
||||||
|
border-left: none;
|
||||||
|
border-right: 3px solid var(--admonitionBorder);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
22. Paperclip Markdown Rendered Content
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .paperclip-mdxeditor-content ul,
|
||||||
|
html[dir="rtl"] .paperclip-mdxeditor-content ol {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: 1.6em;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .paperclip-mdxeditor-content blockquote {
|
||||||
|
border-left: none;
|
||||||
|
border-right: 3px solid var(--border);
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .paperclip-markdown :where(ul, ol) {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: 1.15rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .paperclip-markdown li {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: .2rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .paperclip-markdown blockquote {
|
||||||
|
border-left: none;
|
||||||
|
border-right: .24rem solid var(--border);
|
||||||
|
margin-left: initial;
|
||||||
|
margin-right: 0;
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: .95rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
@supports (color: color-mix(in lab, red, red)) {
|
||||||
|
html[dir="rtl"] .paperclip-markdown blockquote {
|
||||||
|
border-right: .24rem solid color-mix(in oklab, var(--border) 84%, var(--muted-foreground) 16%);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .paperclip-markdown th {
|
||||||
|
text-align: right;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Nested list/ol padding overrides from Tailwind arbitrary selectors */
|
||||||
|
html[dir="rtl"] .\[\&_ol\]\:pl-5 ol {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: calc(var(--spacing) * 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .\[\&_ul\]\:pl-5 ul {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: calc(var(--spacing) * 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
23. CodeMirror (inside MDXEditor) - Cursor & Gutters
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .paperclip-mdxeditor .cm-cursor,
|
||||||
|
html[dir="rtl"] .paperclip-mdxeditor .cm-dropCursor {
|
||||||
|
border-left-color: transparent !important;
|
||||||
|
border-right-color: #cdd6f4 !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] .paperclip-mdxeditor .cm-gutters {
|
||||||
|
border-right: none !important;
|
||||||
|
border-left: 1px solid #313244 !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
24. Sidebar Layout (shadcn/ui sidebar pattern)
|
||||||
|
|
||||||
|
The sidebar CSS variables are defined but the layout depends on the
|
||||||
|
app's component structure. These overrides handle common patterns.
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
/* If sidebar is positioned with left:0, move to right:0 */
|
||||||
|
html[dir="rtl"] [data-sidebar="sidebar"] {
|
||||||
|
left: auto;
|
||||||
|
right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Sidebar rail/resize handle */
|
||||||
|
html[dir="rtl"] [data-sidebar="rail"] {
|
||||||
|
left: auto;
|
||||||
|
right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Main content margin adjustment when sidebar present */
|
||||||
|
html[dir="rtl"] [data-sidebar="content"] {
|
||||||
|
margin-left: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
25. Dialog Overlay - full screen, no directional change needed
|
||||||
|
But ensure overlay covers correctly
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_dialogOverlay_"] {
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
26. Radix UI Popover/Dropdown Transform Origins
|
||||||
|
These use CSS variables, so they auto-adapt. No override needed.
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
27. Group rotation for collapsible triggers (chevron icons)
|
||||||
|
In RTL, a right-pointing chevron should point left by default
|
||||||
|
and rotate when open
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] .group-data-\[state\=open\]\:rotate-90:is(:where(.group)[data-state=open] *) {
|
||||||
|
rotate: -90deg;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
28. General Hebrew typography adjustments
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] input,
|
||||||
|
html[dir="rtl"] textarea,
|
||||||
|
html[dir="rtl"] select {
|
||||||
|
text-align: right;
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] input[type="email"],
|
||||||
|
html[dir="rtl"] input[type="url"],
|
||||||
|
html[dir="rtl"] input[type="number"] {
|
||||||
|
text-align: left;
|
||||||
|
direction: ltr;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Placeholder text alignment */
|
||||||
|
html[dir="rtl"] input::placeholder,
|
||||||
|
html[dir="rtl"] textarea::placeholder {
|
||||||
|
text-align: right;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
29. Scrollbar position (WebKit) - move to left side in RTL
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] ::-webkit-scrollbar {
|
||||||
|
/* Scrollbars auto-flip in RTL for most browsers */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
30. Active SVG translate (press feedback) - flip X direction
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_toolbarToggleItem_"]:active svg,
|
||||||
|
html[dir="rtl"] [class*="_toolbarButton_"]:active svg,
|
||||||
|
html[dir="rtl"] [class*="_actionButton_"]:active svg,
|
||||||
|
html[dir="rtl"] [class*="_tableColumnEditorTrigger_"]:active svg,
|
||||||
|
html[dir="rtl"] [class*="_tableColumnEditorToolbar_"] > button:active svg,
|
||||||
|
html[dir="rtl"] [class*="_toggleGroupRoot_"] button:active svg,
|
||||||
|
html[dir="rtl"] [class*="_addColumnButton_"]:active svg,
|
||||||
|
html[dir="rtl"] [class*="_addRowButton_"]:active svg {
|
||||||
|
transform: translate(-1px, 1px);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
31. Responsive breakpoint overrides
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
@media (min-width: 640px) {
|
||||||
|
html[dir="rtl"] .sm\:flex-row {
|
||||||
|
flex-direction: row-reverse;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (min-width: 768px) {
|
||||||
|
html[dir="rtl"] .md\:flex-row {
|
||||||
|
flex-direction: row-reverse;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (min-width: 1024px) {
|
||||||
|
html[dir="rtl"] .lg\:flex-row {
|
||||||
|
flex-direction: row-reverse;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (min-width: 1280px) {
|
||||||
|
html[dir="rtl"] .xl\:flex-row {
|
||||||
|
flex-direction: row-reverse;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
32. Fix for centered dialogs using left:50% + translate(-50%, -50%)
|
||||||
|
These should remain centered, so override left->right and flip translate
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
html[dir="rtl"] [class*="_dialogContent_"],
|
||||||
|
html[dir="rtl"] [class*="_largeDialogContent_"] {
|
||||||
|
left: auto;
|
||||||
|
right: 50%;
|
||||||
|
transform: translate(50%, -50%);
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes rtl-contentShow {
|
||||||
|
0% {
|
||||||
|
opacity: 0;
|
||||||
|
transform: translate(50%, -48%) scale(.96);
|
||||||
|
}
|
||||||
|
to {
|
||||||
|
opacity: 1;
|
||||||
|
transform: translate(50%, -50%) scale(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
html[dir="rtl"] [class*="_dialogContent_"],
|
||||||
|
html[dir="rtl"] [class*="_largeDialogContent_"] {
|
||||||
|
animation: rtl-contentShow .15s cubic-bezier(.16, 1, .3, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
33. Fix Tailwind space-x utilities
|
||||||
|
These already use margin-inline-start/end, so they should auto-adapt.
|
||||||
|
No override needed for space-x-* classes (they use logical properties).
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
34. Override for the bottom-positioned elements with safe-area-inset
|
||||||
|
These are vertical-only, no RTL swap needed.
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
/* --------------------------------------------------------------------------
|
||||||
|
35. Miscellaneous icon and decorative element adjustments
|
||||||
|
-------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
/* Ensure icons in buttons don't get mirrored unintentionally */
|
||||||
|
html[dir="rtl"] svg {
|
||||||
|
/* Most icons should NOT be mirrored. Only directional icons need it. */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Mirror directional icons (arrows, chevrons) */
|
||||||
|
html[dir="rtl"] [class*="chevron-left"] svg,
|
||||||
|
html[dir="rtl"] [class*="chevron-right"] svg,
|
||||||
|
html[dir="rtl"] [class*="arrow-left"] svg,
|
||||||
|
html[dir="rtl"] [class*="arrow-right"] svg {
|
||||||
|
transform: scaleX(-1);
|
||||||
|
}
|
||||||
918
assets/translate-he.js
Normal file
918
assets/translate-he.js
Normal file
@@ -0,0 +1,918 @@
|
|||||||
|
/**
|
||||||
|
* Paperclip AI - Hebrew Translation Injection
|
||||||
|
* Replaces English UI text with Hebrew after React renders.
|
||||||
|
* Uses MutationObserver to catch route changes and dynamic content.
|
||||||
|
*/
|
||||||
|
(function () {
|
||||||
|
"use strict";
|
||||||
|
|
||||||
|
// =========================================================================
|
||||||
|
// TRANSLATION MAP
|
||||||
|
// =========================================================================
|
||||||
|
const T = {
|
||||||
|
// --- Sidebar / Navigation ---
|
||||||
|
"Dashboard": "לוח בקרה",
|
||||||
|
"Inbox": "תיבת דואר",
|
||||||
|
"Work": "עבודה",
|
||||||
|
"Issues": "משימות",
|
||||||
|
"Routines": "שגרות",
|
||||||
|
"Goals": "יעדים",
|
||||||
|
"Company": "חברה",
|
||||||
|
"Org": "ארגון",
|
||||||
|
"Skills": "כישורים",
|
||||||
|
"Costs": "עלויות",
|
||||||
|
"Activity": "פעילות",
|
||||||
|
"Settings": "הגדרות",
|
||||||
|
"General": "כללי",
|
||||||
|
"Heartbeats": "פעימות",
|
||||||
|
"Experimental": "ניסיוני",
|
||||||
|
"Plugins": "תוספים",
|
||||||
|
"Me": "אני",
|
||||||
|
"Agents": "סוכנים",
|
||||||
|
"Projects": "פרויקטים",
|
||||||
|
"Home": "בית",
|
||||||
|
"Create": "צור",
|
||||||
|
"Not Found": "לא נמצא",
|
||||||
|
"Open sidebar": "פתח סרגל צד",
|
||||||
|
"Close sidebar": "סגור סרגל צד",
|
||||||
|
"Skip to Main Content": "דלג לתוכן הראשי",
|
||||||
|
|
||||||
|
// --- Common Buttons ---
|
||||||
|
"Save": "שמור",
|
||||||
|
"Cancel": "ביטול",
|
||||||
|
"Delete": "מחק",
|
||||||
|
"Edit": "ערוך",
|
||||||
|
"Update": "עדכן",
|
||||||
|
"Close": "סגור",
|
||||||
|
"Confirm": "אשר",
|
||||||
|
"Back": "חזור",
|
||||||
|
"Next": "הבא",
|
||||||
|
"Previous": "הקודם",
|
||||||
|
"Done": "סיום",
|
||||||
|
"Apply": "החל",
|
||||||
|
"Continue": "המשך",
|
||||||
|
"Dismiss": "סגור",
|
||||||
|
"Clear": "נקה",
|
||||||
|
"Reset": "אפס",
|
||||||
|
"Retry": "נסה שוב",
|
||||||
|
"Submit": "שלח",
|
||||||
|
"OK": "אישור",
|
||||||
|
"Yes": "כן",
|
||||||
|
"No": "לא",
|
||||||
|
"Go": "עבור",
|
||||||
|
"Search": "חיפוש",
|
||||||
|
"Filter": "סינון",
|
||||||
|
"Sort": "מיון",
|
||||||
|
"Copy": "העתק",
|
||||||
|
"Download": "הורד",
|
||||||
|
"Upload": "העלה",
|
||||||
|
"Export": "ייצוא",
|
||||||
|
"Import": "ייבוא",
|
||||||
|
"Enable": "הפעל",
|
||||||
|
"Disable": "השבת",
|
||||||
|
"Install": "התקן",
|
||||||
|
"Uninstall": "הסר התקנה",
|
||||||
|
"Start": "התחל",
|
||||||
|
"Stop": "עצור",
|
||||||
|
"Pause": "השהה",
|
||||||
|
"Resume": "חדש",
|
||||||
|
"Run": "הפעל",
|
||||||
|
"Launch": "הפעל",
|
||||||
|
"Approve": "אשר",
|
||||||
|
"Reject": "דחה",
|
||||||
|
"Archive": "ארכיון",
|
||||||
|
"Restore": "שחזר",
|
||||||
|
"Pin": "הצמד",
|
||||||
|
"Revoke": "בטל",
|
||||||
|
"Assign": "הקצה",
|
||||||
|
"Block": "חסום",
|
||||||
|
"Link": "קישור",
|
||||||
|
"View": "צפה",
|
||||||
|
"Show": "הצג",
|
||||||
|
"Hide": "הסתר",
|
||||||
|
"Open": "פתח",
|
||||||
|
"Select": "בחר",
|
||||||
|
"Remove": "הסר",
|
||||||
|
"Comment": "תגובה",
|
||||||
|
"Restart": "הפעל מחדש",
|
||||||
|
"Schedule": "תזמן",
|
||||||
|
"Configure": "הגדר",
|
||||||
|
"Choose": "בחר",
|
||||||
|
|
||||||
|
// --- Action Buttons ---
|
||||||
|
"Save changes": "שמור שינויים",
|
||||||
|
"Save Configuration": "שמור הגדרות",
|
||||||
|
"Save note": "שמור הערה",
|
||||||
|
"Save routine": "שמור שגרה",
|
||||||
|
"Save trigger": "שמור טריגר",
|
||||||
|
"Save failed": "השמירה נכשלה",
|
||||||
|
"Add Agent": "הוסף סוכן",
|
||||||
|
"Add Goal": "הוסף יעד",
|
||||||
|
"Add Project": "הוסף פרויקט",
|
||||||
|
"Add company": "הוסף חברה",
|
||||||
|
"Add item": "הוסף פריט",
|
||||||
|
"Add trigger": "הוסף טריגר",
|
||||||
|
"Add a new agent": "הוסף סוכן חדש",
|
||||||
|
"Add a skill source": "הוסף מקור כישורים",
|
||||||
|
"Add a short note": "הוסף הערה קצרה",
|
||||||
|
"Add a comment...": "הוסף תגובה...",
|
||||||
|
"Add a description...": "הוסף תיאור...",
|
||||||
|
"Add description...": "הוסף תיאור...",
|
||||||
|
"Add instructions...": "הוסף הוראות...",
|
||||||
|
"Adding...": "מוסיף...",
|
||||||
|
"Create Issue": "צור משימה",
|
||||||
|
"Create Item": "צור פריט",
|
||||||
|
"Create Account": "צור חשבון",
|
||||||
|
"Create API Key": "צור מפתח API",
|
||||||
|
"Create agent": "צור סוכן",
|
||||||
|
"Create document": "צור מסמך",
|
||||||
|
"Create goal": "צור יעד",
|
||||||
|
"Create label": "צור תווית",
|
||||||
|
"Create one": "צור אחד",
|
||||||
|
"Create one here": "צור כאן",
|
||||||
|
"Create project": "צור פרויקט",
|
||||||
|
"Create routine": "צור שגרה",
|
||||||
|
"Create skill": "צור כישור",
|
||||||
|
"Create new agent": "צור סוכן חדש",
|
||||||
|
"Create new company": "צור חברה חדשה",
|
||||||
|
"Create new issue": "צור משימה חדשה",
|
||||||
|
"Create new project": "צור פרויקט חדש",
|
||||||
|
"Create another company": "צור חברה נוספת",
|
||||||
|
"Create a new agent": "צור סוכן חדש",
|
||||||
|
"Create your Paperclip account": "צור את חשבון Paperclip שלך",
|
||||||
|
"Create your first agent": "צור את הסוכן הראשון שלך",
|
||||||
|
"Create your first company": "צור את החברה הראשונה שלך",
|
||||||
|
"Delete Company": "מחק חברה",
|
||||||
|
"Delete attachment": "מחק קובץ מצורף",
|
||||||
|
"Delete document": "מחק מסמך",
|
||||||
|
"Delete failed": "המחיקה נכשלה",
|
||||||
|
"Delete image": "מחק תמונה",
|
||||||
|
"Delete issue": "מחק משימה",
|
||||||
|
"Edit document": "ערוך מסמך",
|
||||||
|
"Edit image": "ערוך תמונה",
|
||||||
|
"Copy Agent ID": "העתק מזהה סוכן",
|
||||||
|
"Copy to clipboard": "העתק ללוח",
|
||||||
|
"Copy snippet": "העתק קטע",
|
||||||
|
"Copy document": "העתק מסמך",
|
||||||
|
"Approve CLI access": "אשר גישת CLI",
|
||||||
|
"Approve Paperclip CLI access": "אשר גישת Paperclip CLI",
|
||||||
|
"Approving...": "מאשר...",
|
||||||
|
"Archive company": "העבר חברה לארכיון",
|
||||||
|
"Assign Task": "הקצה משימה",
|
||||||
|
"Assign to me": "הקצה לי",
|
||||||
|
"Assign to requester": "הקצה למבקש",
|
||||||
|
"Import company": "ייבא חברה",
|
||||||
|
"Import complete": "הייבוא הושלם",
|
||||||
|
"Import failed": "הייבוא נכשל",
|
||||||
|
"Import preview": "תצוגה מקדימה של ייבוא",
|
||||||
|
"Import source": "מקור ייבוא",
|
||||||
|
"Export company": "ייצא חברה",
|
||||||
|
"Export downloaded": "הייצוא הורד",
|
||||||
|
"Export failed": "הייצוא נכשל",
|
||||||
|
"Install Plugin": "התקן תוסף",
|
||||||
|
"Install Example": "התקן דוגמה",
|
||||||
|
"Install update": "התקן עדכון",
|
||||||
|
"Uninstall Plugin": "הסר תוסף",
|
||||||
|
"Run now": "הפעל עכשיו",
|
||||||
|
"Run routine": "הפעל שגרה",
|
||||||
|
"Run Activity": "הפעל פעילות",
|
||||||
|
"Run Heartbeat": "הפעל פעימה",
|
||||||
|
"Open board": "פתח לוח",
|
||||||
|
"Open budgets": "פתח תקציבים",
|
||||||
|
"Open command palette": "פתח לוח פקודות",
|
||||||
|
"Open Command Palette": "פתח לוח פקודות",
|
||||||
|
"Open dashboard": "פתח לוח בקרה",
|
||||||
|
"Open docs": "פתח מסמכים",
|
||||||
|
"Open Settings": "פתח הגדרות",
|
||||||
|
"Open Issues": "משימות פתוחות",
|
||||||
|
"Open Side Panel": "פתח פאנל צדי",
|
||||||
|
"View agent": "צפה בסוכן",
|
||||||
|
"View details": "צפה בפרטים",
|
||||||
|
"View full error": "צפה בשגיאה מלאה",
|
||||||
|
"View inbox": "צפה בתיבת דואר",
|
||||||
|
"View run": "צפה בהרצה",
|
||||||
|
"Mark all as read": "סמן הכל כנקרא",
|
||||||
|
"Mark as done": "סמן כבוצע",
|
||||||
|
"Mark as read": "סמן כנקרא",
|
||||||
|
"Clear all": "נקה הכל",
|
||||||
|
"Clear repo": "נקה מאגר",
|
||||||
|
"Clear local folder": "נקה תיקיה מקומית",
|
||||||
|
"Sign in": "התחבר",
|
||||||
|
"Sign in required": "נדרשת התחברות",
|
||||||
|
"Sign in to Paperclip": "התחבר ל-Paperclip",
|
||||||
|
"Sign in / Create account": "התחבר / צור חשבון",
|
||||||
|
"Go home": "חזור לדף הבית",
|
||||||
|
"Back to all workspaces": "חזור לכל סביבות העבודה",
|
||||||
|
"Back to approvals": "חזור לאישורים",
|
||||||
|
"Back to runs": "חזור להרצות",
|
||||||
|
"Back to workspaces": "חזור לסביבות עבודה",
|
||||||
|
"Check for updates": "בדוק עדכונים",
|
||||||
|
"Start Onboarding": "התחל הקמה",
|
||||||
|
"Stop editing": "הפסק עריכה",
|
||||||
|
"Deploy to production": "פרוס לייצור",
|
||||||
|
"Restart Required": "נדרש הפעלה מחדש",
|
||||||
|
"Reset Sessions": "אפס הפעלות",
|
||||||
|
"Reset defaults": "אפס ברירות מחדל",
|
||||||
|
"Reset filters": "אפס מסננים",
|
||||||
|
"Download document": "הורד מסמך",
|
||||||
|
"Upload attachment": "העלה קובץ מצורף",
|
||||||
|
"Upload an image": "העלה תמונה",
|
||||||
|
"Upload failed": "ההעלאה נכשלה",
|
||||||
|
"Filter Bar": "סרגל סינון",
|
||||||
|
"Filter by agent name": "סנן לפי שם סוכן",
|
||||||
|
"Filter by type": "סנן לפי סוג",
|
||||||
|
"Filter skills": "סנן כישורים",
|
||||||
|
"Show properties": "הצג מאפיינים",
|
||||||
|
"Show secret": "הצג סוד",
|
||||||
|
"Hide secret": "הסתר סוד",
|
||||||
|
"Show full log": "הצג יומן מלא",
|
||||||
|
"Hide full log": "הסתר יומן מלא",
|
||||||
|
"Set repo": "הגדר מאגר",
|
||||||
|
"Change repo": "שנה מאגר",
|
||||||
|
"Submit join request": "שלח בקשת הצטרפות",
|
||||||
|
"Join request submitted": "בקשת ההצטרפות נשלחה",
|
||||||
|
"Accept bootstrap invite": "קבל הזמנת הקמה",
|
||||||
|
"Return to latest": "חזור לעדכני",
|
||||||
|
"Jump to live": "עבור לשידור חי",
|
||||||
|
"Select company": "בחר חברה",
|
||||||
|
"Select model": "בחר מודל",
|
||||||
|
"Select status": "בחר סטטוס",
|
||||||
|
"Select an option": "בחר אפשרות",
|
||||||
|
"Watch issue": "עקוב אחר משימה",
|
||||||
|
"Wake now": "העיר עכשיו",
|
||||||
|
"Keep my draft": "שמור את הטיוטה שלי",
|
||||||
|
"Keep paused": "השאר מושהה",
|
||||||
|
"Discard Draft": "מחק טיוטה",
|
||||||
|
|
||||||
|
// --- Navigation Tabs ---
|
||||||
|
"Overview": "סקירה כללית",
|
||||||
|
"Instructions": "הוראות",
|
||||||
|
"Configuration": "הגדרות",
|
||||||
|
"Runs": "הרצות",
|
||||||
|
"Budget": "תקציב",
|
||||||
|
"Workspaces": "סביבות עבודה",
|
||||||
|
"All": "הכל",
|
||||||
|
"Active": "פעיל",
|
||||||
|
"Paused": "מושהה",
|
||||||
|
"Error": "שגיאה",
|
||||||
|
"Recent": "אחרונים",
|
||||||
|
"Mine": "שלי",
|
||||||
|
"Unread": "לא נקרא",
|
||||||
|
"Status": "סטטוס",
|
||||||
|
|
||||||
|
// --- Status Labels ---
|
||||||
|
"Backlog": "רשימת המתנה",
|
||||||
|
"Todo": "לביצוע",
|
||||||
|
"In Progress": "בביצוע",
|
||||||
|
"In Review": "בסקירה",
|
||||||
|
"Planned": "מתוכנן",
|
||||||
|
"Completed": "הושלם",
|
||||||
|
"Cancelled": "בוטל",
|
||||||
|
"Critical": "קריטי",
|
||||||
|
"High": "גבוה",
|
||||||
|
"Medium": "בינוני",
|
||||||
|
"Low": "נמוך",
|
||||||
|
"Default": "ברירת מחדל",
|
||||||
|
"Blocked": "חסום",
|
||||||
|
"Queued": "בתור",
|
||||||
|
"Running": "פועל",
|
||||||
|
"Enabled": "מופעל",
|
||||||
|
"Disabled": "מושבת",
|
||||||
|
"Pending": "ממתין",
|
||||||
|
"Resolved": "נפתר",
|
||||||
|
"Unknown": "לא ידוע",
|
||||||
|
"New": "חדש",
|
||||||
|
"Archived": "בארכיון",
|
||||||
|
"Passed": "עבר",
|
||||||
|
"Failed": "נכשל",
|
||||||
|
"Managed": "מנוהל",
|
||||||
|
"Live": "חי",
|
||||||
|
"Observed": "נצפה",
|
||||||
|
"Cached": "במטמון",
|
||||||
|
"Sealed": "חתום",
|
||||||
|
"Recommended": "מומלץ",
|
||||||
|
"Beta": "בטא",
|
||||||
|
"Unlimited budget": "תקציב ללא הגבלה",
|
||||||
|
"Under budget": "בתוך התקציב",
|
||||||
|
"Out of date": "לא מעודכן",
|
||||||
|
"Up to date": "מעודכן",
|
||||||
|
"Not set.": "לא הוגדר.",
|
||||||
|
"Not installed": "לא מותקן",
|
||||||
|
|
||||||
|
// --- Thinking Effort ---
|
||||||
|
"Auto": "אוטומטי",
|
||||||
|
"Minimal": "מינימלי",
|
||||||
|
"X-High": "גבוה מאוד",
|
||||||
|
"Max": "מקסימום",
|
||||||
|
|
||||||
|
// --- Workspace Options ---
|
||||||
|
"Project default": "ברירת מחדל של פרויקט",
|
||||||
|
"New isolated workspace": "סביבת עבודה מבודדת חדשה",
|
||||||
|
"Reuse existing workspace": "שימוש חוזר בסביבה קיימת",
|
||||||
|
"Remote git repo": "מאגר git מרוחק",
|
||||||
|
"Local git checkout": "checkout מקומי של git",
|
||||||
|
"Local non-git path": "נתיב מקומי ללא git",
|
||||||
|
"Remote-managed workspace": "סביבת עבודה מנוהלת מרחוק",
|
||||||
|
"Git worktree": "Git worktree",
|
||||||
|
"Local folder": "תיקיה מקומית",
|
||||||
|
|
||||||
|
// --- Frequency Options ---
|
||||||
|
"Every minute": "כל דקה",
|
||||||
|
"Every hour": "כל שעה",
|
||||||
|
"Every day": "כל יום",
|
||||||
|
"Weekdays": "ימי חול",
|
||||||
|
"Weekly": "שבועי",
|
||||||
|
"Monthly": "חודשי",
|
||||||
|
"Custom (cron)": "מותאם אישית (cron)",
|
||||||
|
|
||||||
|
// --- Dashboard Cards ---
|
||||||
|
"Agents Enabled": "סוכנים מופעלים",
|
||||||
|
"Tasks In Progress": "משימות בביצוע",
|
||||||
|
"Month Spend": "הוצאות החודש",
|
||||||
|
"Pending Approvals": "אישורים ממתינים",
|
||||||
|
"Active Agents": "סוכנים פעילים",
|
||||||
|
"Active incidents": "תקלות פעילות",
|
||||||
|
"Active Keys": "מפתחות פעילים",
|
||||||
|
"Companies": "חברות",
|
||||||
|
"Live Runs": "הרצות חיות",
|
||||||
|
"Recent Activity": "פעילות אחרונה",
|
||||||
|
"Recent Issues": "משימות אחרונות",
|
||||||
|
"Recent Tasks": "משימות אחרונות",
|
||||||
|
"Success Rate": "אחוז הצלחה",
|
||||||
|
"Failed runs": "הרצות שנכשלו",
|
||||||
|
"Cost Summary": "סיכום עלויות",
|
||||||
|
|
||||||
|
// --- Page Titles ---
|
||||||
|
"Company Settings": "הגדרות חברה",
|
||||||
|
"Instance Settings": "הגדרות מופע",
|
||||||
|
"Approvals": "אישורים",
|
||||||
|
"Plugin Manager": "מנהל תוספים",
|
||||||
|
"Available Plugins": "תוספים זמינים",
|
||||||
|
"Installed Plugins": "תוספים מותקנים",
|
||||||
|
"Design Guide": "מדריך עיצוב",
|
||||||
|
"Org Chart": "מבנה ארגוני",
|
||||||
|
"Finance": "כספים",
|
||||||
|
"Budgets": "תקציבים",
|
||||||
|
"Budget control plane": "מישור בקרת תקציב",
|
||||||
|
"Scheduler Heartbeats": "פעימות מתזמן",
|
||||||
|
"Run Detail": "פרטי הרצה",
|
||||||
|
"Issue List": "רשימת משימות",
|
||||||
|
"Issue Properties": "מאפייני משימה",
|
||||||
|
"Execution Workspaces": "סביבות ביצוע",
|
||||||
|
"Company Packages": "חבילות חברה",
|
||||||
|
"Keyboard Shortcuts": "קיצורי מקלדת",
|
||||||
|
"Danger Zone": "אזור מסוכן",
|
||||||
|
"New Agent": "סוכן חדש",
|
||||||
|
"New Company": "חברה חדשה",
|
||||||
|
"New Issue": "משימה חדשה",
|
||||||
|
"New document": "מסמך חדש",
|
||||||
|
"New issue": "משימה חדשה",
|
||||||
|
"New project": "פרויקט חדש",
|
||||||
|
"New routine": "שגרה חדשה",
|
||||||
|
"Revision history": "היסטוריית גרסאות",
|
||||||
|
|
||||||
|
// --- Form Labels ---
|
||||||
|
"Name": "שם",
|
||||||
|
"Title": "כותרת",
|
||||||
|
"Description": "תיאור",
|
||||||
|
"Priority": "עדיפות",
|
||||||
|
"Assignee": "מוקצה",
|
||||||
|
"Project": "פרויקט",
|
||||||
|
"Labels": "תוויות",
|
||||||
|
"Created": "נוצר",
|
||||||
|
"Updated": "עודכן",
|
||||||
|
"Target Date": "תאריך יעד",
|
||||||
|
"Start date": "תאריך התחלה",
|
||||||
|
"Lead": "אחראי",
|
||||||
|
"Author": "מחבר",
|
||||||
|
"Email": "אימייל",
|
||||||
|
"Password": "סיסמה",
|
||||||
|
"Company name": "שם חברה",
|
||||||
|
"Agent name": "שם סוכן",
|
||||||
|
"Branch name": "שם ענף",
|
||||||
|
"Branch template": "תבנית ענף",
|
||||||
|
"Base ref": "הפניית בסיס",
|
||||||
|
"Repo URL": "כתובת מאגר",
|
||||||
|
"Brand color": "צבע מותג",
|
||||||
|
"Command": "פקודה",
|
||||||
|
"Adapter type": "סוג מתאם",
|
||||||
|
"Prompt Template": "תבנית פרומפט",
|
||||||
|
"Environment variables": "משתני סביבה",
|
||||||
|
"Timeout (sec)": "זמן קצוב (שניות)",
|
||||||
|
"Max concurrent runs": "הרצות מקבילות מקסימום",
|
||||||
|
"Max turns per run": "סיבובים מקסימום להרצה",
|
||||||
|
"Model": "מודל",
|
||||||
|
"Thinking effort": "מאמץ חשיבה",
|
||||||
|
"Reports to": "מדווח ל",
|
||||||
|
"Capabilities": "יכולות",
|
||||||
|
"Capabilities (optional)": "יכולות (אופציונלי)",
|
||||||
|
"Role": "תפקיד",
|
||||||
|
"Budget (USD)": "תקציב (דולר)",
|
||||||
|
"New budget (USD)": "תקציב חדש (דולר)",
|
||||||
|
"Heartbeat on interval": "פעימה במרווחי זמן",
|
||||||
|
"Wake on demand": "התעוררות לפי דרישה",
|
||||||
|
"Default model": "מודל ברירת מחדל",
|
||||||
|
"Collision strategy": "אסטרטגיית התנגשות",
|
||||||
|
"Description (optional)": "תיאור (אופציונלי)",
|
||||||
|
"Workspace name": "שם סביבת עבודה",
|
||||||
|
"Execution workspace": "סביבת ביצוע",
|
||||||
|
"Provision command": "פקודת הקמה",
|
||||||
|
"Teardown command": "פקודת פירוק",
|
||||||
|
"Cleanup command": "פקודת ניקוי",
|
||||||
|
"Runtime services": "שירותי ריצה",
|
||||||
|
"Plugin Key": "מפתח תוסף",
|
||||||
|
"Plugin ID": "מזהה תוסף",
|
||||||
|
"Key": "מפתח",
|
||||||
|
"Skill name": "שם כישור",
|
||||||
|
"Document key": "מפתח מסמך",
|
||||||
|
"Variables": "משתנים",
|
||||||
|
"Default value": "ערך ברירת מחדל",
|
||||||
|
"Source": "מקור",
|
||||||
|
"Mode": "מצב",
|
||||||
|
"Kind": "סוג",
|
||||||
|
"Type": "סוג",
|
||||||
|
"Concurrency": "מקביליות",
|
||||||
|
"Version": "גרסה",
|
||||||
|
"PID": "PID",
|
||||||
|
"Uptime": "זמן פעילות",
|
||||||
|
"Auto-Restart On": "הפעלה מחדש אוטומטית",
|
||||||
|
"AI feedback sharing": "שיתוף משוב AI",
|
||||||
|
"Feedback Sharing": "שיתוף משוב",
|
||||||
|
|
||||||
|
// --- Placeholders ---
|
||||||
|
"Search icons...": "חפש אייקונים...",
|
||||||
|
"Search issues, agents, projects...": "חפש משימות, סוכנים, פרויקטים...",
|
||||||
|
"Search issues...": "חפש משימות...",
|
||||||
|
"Search assignees...": "חפש מוקצים...",
|
||||||
|
"Search labels...": "חפש תוויות...",
|
||||||
|
"Search projects...": "חפש פרויקטים...",
|
||||||
|
"Search models...": "חפש מודלים...",
|
||||||
|
"Search files...": "חפש קבצים...",
|
||||||
|
"Search inbox\u2026": "חפש בתיבת דואר\u2026",
|
||||||
|
"Type a command or search...": "הקלד פקודה או חפש...",
|
||||||
|
"Issue title": "כותרת משימה",
|
||||||
|
"Project name": "שם פרויקט",
|
||||||
|
"Target date": "תאריך יעד",
|
||||||
|
"Goal title": "כותרת יעד",
|
||||||
|
"Leave a comment...": "השאר תגובה...",
|
||||||
|
"Write something...": "כתוב משהו...",
|
||||||
|
"Enter a name": "הזן שם",
|
||||||
|
"Describe...": "תאר...",
|
||||||
|
"Choose a value": "בחר ערך",
|
||||||
|
"Choose frequency...": "בחר תדירות...",
|
||||||
|
"Category": "קטגוריה",
|
||||||
|
"Approval status": "סטטוס אישור",
|
||||||
|
"Routine title": "כותרת שגרה",
|
||||||
|
"Optional title": "כותרת אופציונלית",
|
||||||
|
"Markdown body": "גוף Markdown",
|
||||||
|
"New label": "תווית חדשה",
|
||||||
|
"Short description": "תיאור קצר",
|
||||||
|
"Optional company description": "תיאור חברה אופציונלי",
|
||||||
|
"Execution workspace name": "שם סביבת ביצוע",
|
||||||
|
"NPM Package Name": "שם חבילת NPM",
|
||||||
|
|
||||||
|
// --- Empty States ---
|
||||||
|
"No results found.": "לא נמצאו תוצאות.",
|
||||||
|
"No issues": "אין משימות",
|
||||||
|
"No labels": "אין תוויות",
|
||||||
|
"No goal": "אין יעד",
|
||||||
|
"No project": "אין פרויקט",
|
||||||
|
"No parent": "אין הורה",
|
||||||
|
"No manager": "אין מנהל",
|
||||||
|
"No assignee": "אין מוקצה",
|
||||||
|
"No value": "אין ערך",
|
||||||
|
"No default": "אין ברירת מחדל",
|
||||||
|
"No runs yet": "אין הרצות עדיין",
|
||||||
|
"No runs yet.": "אין הרצות עדיין.",
|
||||||
|
"No revisions yet": "אין גרסאות עדיין",
|
||||||
|
"No icons match": "לא נמצאו אייקונים",
|
||||||
|
"No agents match the selected filter.": "אין סוכנים שתואמים למסנן שנבחר.",
|
||||||
|
"No agents attached": "לא צורפו סוכנים",
|
||||||
|
"No active API keys.": "אין מפתחות API פעילים.",
|
||||||
|
"No activity yet.": "אין פעילות עדיין.",
|
||||||
|
"No plugins installed": "לא הותקנו תוספים",
|
||||||
|
"No goals.": "אין יעדים.",
|
||||||
|
"No tasks yet.": "אין משימות עדיין.",
|
||||||
|
"No triggers configured yet.": "לא הוגדרו טריגרים עדיין.",
|
||||||
|
"No description": "אין תיאור",
|
||||||
|
"No diagnostics": "אין אבחנות",
|
||||||
|
"No company selected": "לא נבחרה חברה",
|
||||||
|
"No cost data yet.": "אין נתוני עלויות עדיין.",
|
||||||
|
"No cost events yet.": "אין אירועי עלות עדיין.",
|
||||||
|
"No items added yet.": "לא נוספו פריטים עדיין.",
|
||||||
|
"No recent agent runs.": "אין הרצות סוכנים אחרונות.",
|
||||||
|
"No recent issues.": "אין משימות אחרונות.",
|
||||||
|
"No sub-goals.": "אין תת-יעדים.",
|
||||||
|
"No sub-issues.": "אין תת-משימות.",
|
||||||
|
"None": "ללא",
|
||||||
|
"Unassigned": "לא מוקצה",
|
||||||
|
"You have no agents.": "אין לך סוכנים.",
|
||||||
|
"No unsaved changes.": "אין שינויים שלא נשמרו.",
|
||||||
|
"No configuration options available.": "אין אפשרויות הגדרה זמינות.",
|
||||||
|
|
||||||
|
// --- Loading States ---
|
||||||
|
"Loading...": "טוען...",
|
||||||
|
"Loading\u2026": "טוען\u2026",
|
||||||
|
"Loading companies...": "טוען חברות...",
|
||||||
|
"Loading plugins...": "טוען תוספים...",
|
||||||
|
"Loading revisions...": "טוען גרסאות...",
|
||||||
|
"Loading workspaces...": "טוען סביבות עבודה...",
|
||||||
|
"Loading workspace\u2026": "טוען סביבת עבודה\u2026",
|
||||||
|
"Loading run logs...": "טוען יומני הרצה...",
|
||||||
|
"Loading log...": "טוען יומן...",
|
||||||
|
"Loading keys...": "טוען מפתחות...",
|
||||||
|
"Loading invite...": "טוען הזמנה...",
|
||||||
|
"Loading plugin details...": "טוען פרטי תוסף...",
|
||||||
|
"Checking health...": "בודק תקינות...",
|
||||||
|
"Uploading logo...": "מעלה לוגו...",
|
||||||
|
"Building export...": "בונה ייצוא...",
|
||||||
|
|
||||||
|
// --- Toast & Notifications ---
|
||||||
|
"Copied!": "הועתק!",
|
||||||
|
"Saved": "נשמר",
|
||||||
|
"Approval confirmed": "האישור אושר",
|
||||||
|
"CLI access approved": "גישת CLI אושרה",
|
||||||
|
"Bootstrap complete": "ההקמה הושלמה",
|
||||||
|
"Action failed": "הפעולה נכשלה",
|
||||||
|
"Comment failed": "התגובה נכשלה",
|
||||||
|
"Copy failed": "ההעתקה נכשלה",
|
||||||
|
"Archive failed": "הארכוב נכשל",
|
||||||
|
"Approve failed": "האישור נכשל",
|
||||||
|
"Reject failed": "הדחייה נכשלה",
|
||||||
|
"Update failed": "העדכון נכשל",
|
||||||
|
"Routine created": "השגרה נוצרה",
|
||||||
|
"Routine saved": "השגרה נשמרה",
|
||||||
|
"Routine run failed": "הרצת השגרה נכשלה",
|
||||||
|
"Routine run started": "הרצת השגרה החלה",
|
||||||
|
"Skill created": "הכישור נוצר",
|
||||||
|
"Skill saved": "הכישור נשמר",
|
||||||
|
"Skill updated": "הכישור עודכן",
|
||||||
|
"Plugin installed successfully": "התוסף הותקן בהצלחה",
|
||||||
|
"Plugin uninstalled successfully": "התוסף הוסר בהצלחה",
|
||||||
|
"Plugin enabled": "התוסף הופעל",
|
||||||
|
"Plugin disabled": "התוסף הושבת",
|
||||||
|
"Plugin error": "שגיאת תוסף",
|
||||||
|
"Trigger added": "הטריגר נוסף",
|
||||||
|
"Trigger deleted": "הטריגר נמחק",
|
||||||
|
"Trigger saved": "הטריגר נשמר",
|
||||||
|
"Run completed": "ההרצה הושלמה",
|
||||||
|
"Run failed": "ההרצה נכשלה",
|
||||||
|
"Command failed": "הפקודה נכשלה",
|
||||||
|
"Invite not available": "ההזמנה לא זמינה",
|
||||||
|
"Invite not found": "ההזמנה לא נמצאה",
|
||||||
|
"Interrupt requested": "התבקשה הפסקה",
|
||||||
|
"Interrupt failed": "ההפסקה נכשלה",
|
||||||
|
|
||||||
|
// --- Error Messages ---
|
||||||
|
"An error was thrown.": "אירעה שגיאה.",
|
||||||
|
"Authentication failed": "ההתחברות נכשלה",
|
||||||
|
"Unknown error": "שגיאה לא ידועה",
|
||||||
|
"Invalid JSON.": "JSON לא תקין.",
|
||||||
|
"Failed to create issue. Try again.": "יצירת המשימה נכשלה. נסה שוב.",
|
||||||
|
"Failed to create company": "יצירת החברה נכשלה",
|
||||||
|
"Failed to create agent": "יצירת הסוכן נכשלה",
|
||||||
|
"Failed to save": "השמירה נכשלה",
|
||||||
|
"Failed to approve": "האישור נכשל",
|
||||||
|
"Failed to reject": "הדחייה נכשלה",
|
||||||
|
"Instance setup required": "נדרשת הגדרת מופע",
|
||||||
|
|
||||||
|
// --- Dialog & Confirmation ---
|
||||||
|
"Delete this company and all its data? This cannot be undone.": "למחוק חברה זו וכל הנתונים שלה? לא ניתן לבטל פעולה זו.",
|
||||||
|
"Delete this document? This cannot be undone.": "למחוק מסמך זה? לא ניתן לבטל פעולה זו.",
|
||||||
|
"Mark all as read?": "לסמן הכל כנקרא?",
|
||||||
|
"Already have an account?": "כבר יש לך חשבון?",
|
||||||
|
|
||||||
|
// --- Section Headings ---
|
||||||
|
"Actions": "פעולות",
|
||||||
|
"Advanced": "מתקדם",
|
||||||
|
"Alerts": "התראות",
|
||||||
|
"Appearance": "מראה",
|
||||||
|
"Attachments": "קבצים מצורפים",
|
||||||
|
"Automation": "אוטומציה",
|
||||||
|
"Categories": "קטגוריות",
|
||||||
|
"Cleanup": "ניקוי",
|
||||||
|
"Codebase": "בסיס קוד",
|
||||||
|
"Comments": "תגובות",
|
||||||
|
"Company skills": "כישורי חברה",
|
||||||
|
"Config": "הגדרות",
|
||||||
|
"Context": "הקשר",
|
||||||
|
"Controls": "בקרה",
|
||||||
|
"Credits": "זיכויים",
|
||||||
|
"Debits": "חיובים",
|
||||||
|
"Details": "פרטים",
|
||||||
|
"Documents": "מסמכים",
|
||||||
|
"Environment": "סביבה",
|
||||||
|
"Error Details": "פרטי שגיאה",
|
||||||
|
"Files": "קבצים",
|
||||||
|
"Filters": "מסננים",
|
||||||
|
"Git status": "סטטוס Git",
|
||||||
|
"Hiring": "גיוס",
|
||||||
|
"Identity": "זהות",
|
||||||
|
"Invites": "הזמנות",
|
||||||
|
"Invocation": "הפעלה",
|
||||||
|
"Join requests": "בקשות הצטרפות",
|
||||||
|
"Lifecycle": "מחזור חיים",
|
||||||
|
"Linked Issues": "משימות מקושרות",
|
||||||
|
"Linked issues": "משימות מקושרות",
|
||||||
|
"Options": "אפשרויות",
|
||||||
|
"Output": "פלט",
|
||||||
|
"Owner": "בעלים",
|
||||||
|
"Permissions": "הרשאות",
|
||||||
|
"Properties": "מאפיינים",
|
||||||
|
"Providers": "ספקים",
|
||||||
|
"Quick filters": "מסננים מהירים",
|
||||||
|
"Recent financial events": "אירועי כספים אחרונים",
|
||||||
|
"Recent operations": "פעולות אחרונות",
|
||||||
|
"Remaining": "נותר",
|
||||||
|
"Result": "תוצאה",
|
||||||
|
"Revoked Keys": "מפתחות שבוטלו",
|
||||||
|
"Runtime services": "שירותי ריצה",
|
||||||
|
"Selected skills": "כישורים נבחרים",
|
||||||
|
"Summary": "סיכום",
|
||||||
|
"Tokens": "אסימונים",
|
||||||
|
"Unsaved changes": "שינויים שלא נשמרו",
|
||||||
|
"Warnings": "אזהרות",
|
||||||
|
"Workspace context": "הקשר סביבת עבודה",
|
||||||
|
"Worktree": "עץ עבודה",
|
||||||
|
|
||||||
|
// --- Table/List Headers ---
|
||||||
|
"Action": "פעולה",
|
||||||
|
"Agent": "סוכן",
|
||||||
|
"Branch": "ענף",
|
||||||
|
"Cost": "עלות",
|
||||||
|
"Created by": "נוצר על ידי",
|
||||||
|
"Current": "נוכחי",
|
||||||
|
"Current state": "מצב נוכחי",
|
||||||
|
"Date": "תאריך",
|
||||||
|
"Input tokens": "אסימוני קלט",
|
||||||
|
"Output tokens": "אסימוני פלט",
|
||||||
|
"Cached tokens": "אסימונים ממטמון",
|
||||||
|
"Last Crash": "קריסה אחרונה",
|
||||||
|
"Last run": "הרצה אחרונה",
|
||||||
|
"Overall": "כולל",
|
||||||
|
"Requested by": "התבקש על ידי",
|
||||||
|
"Task": "משימה",
|
||||||
|
"Total": "סך הכל",
|
||||||
|
"Total cost": "עלות כוללת",
|
||||||
|
"Used by": "בשימוש על ידי",
|
||||||
|
|
||||||
|
// --- Misc UI Labels ---
|
||||||
|
"About": "אודות",
|
||||||
|
"Adapter": "מתאם",
|
||||||
|
"After": "אחרי",
|
||||||
|
"Before": "לפני",
|
||||||
|
"Board view": "תצוגת לוח",
|
||||||
|
"Coming soon": "בקרוב",
|
||||||
|
"Documentation": "תיעוד",
|
||||||
|
"Earlier": "מוקדם יותר",
|
||||||
|
"Estimated": "משוער",
|
||||||
|
"External": "חיצוני",
|
||||||
|
"Human": "אנושי",
|
||||||
|
"My recent issues": "המשימות האחרונות שלי",
|
||||||
|
"Optional": "אופציונלי",
|
||||||
|
"Per issue": "למשימה",
|
||||||
|
"Per run": "להרצה",
|
||||||
|
"Secret": "סוד",
|
||||||
|
"See All \u2192": "ראה הכל \u2192",
|
||||||
|
"Small": "קטן",
|
||||||
|
"Large": "גדול",
|
||||||
|
"User": "משתמש",
|
||||||
|
"View details \u2192": "צפה בפרטים \u2192",
|
||||||
|
"All approval statuses": "כל סטטוסי האישור",
|
||||||
|
"All categories": "כל הקטגוריות",
|
||||||
|
"All providers": "כל הספקים",
|
||||||
|
"All types": "כל הסוגים",
|
||||||
|
"All Time": "כל הזמנים",
|
||||||
|
"Last 14 days": "14 ימים אחרונים",
|
||||||
|
"Automation enabled.": "אוטומציה מופעלת.",
|
||||||
|
"Automation paused.": "אוטומציה מושהית.",
|
||||||
|
"Mobile navigation": "ניווט נייד",
|
||||||
|
|
||||||
|
// --- Command Palette ---
|
||||||
|
"Pages": "דפים",
|
||||||
|
|
||||||
|
// --- Onboarding ---
|
||||||
|
"Bootstrap your Paperclip instance": "הקם את מופע ה-Paperclip שלך",
|
||||||
|
"Name your company": "תן שם לחברה שלך",
|
||||||
|
"This is the organization your agents will work for.": "זהו הארגון שעבורו הסוכנים שלך יעבדו.",
|
||||||
|
"This will be the CEO": "זה יהיה המנכ\"ל",
|
||||||
|
"Give it something to do": "תן לו משהו לעשות",
|
||||||
|
"Ready to launch": "מוכן להפעלה",
|
||||||
|
"Welcome to Paperclip. Set up your first company and agent to get started.": "ברוכים הבאים ל-Paperclip. הקם את החברה והסוכן הראשונים שלך כדי להתחיל.",
|
||||||
|
"I want advanced configuration myself": "אני רוצה להגדיר בעצמי הגדרות מתקדמות",
|
||||||
|
"Get started by creating a company.": "התחל ביצירת חברה.",
|
||||||
|
|
||||||
|
// --- Descriptions ---
|
||||||
|
"Choose how this agent will run tasks.": "בחר כיצד סוכן זה יריץ משימות.",
|
||||||
|
"Choose your adapter type for advanced setup.": "בחר את סוג המתאם להגדרה מתקדמת.",
|
||||||
|
"Plugins are alpha.": "התוספים בשלב אלפא.",
|
||||||
|
"Read our terms of service": "קרא את תנאי השירות שלנו",
|
||||||
|
"Select a company first.": "בחר חברה תחילה.",
|
||||||
|
"Sharing is currently disabled.": "השיתוף מושבת כרגע.",
|
||||||
|
"Don't allow": "אל תאפשר",
|
||||||
|
"Always allow": "אפשר תמיד",
|
||||||
|
"What could have been better?": "מה יכול היה להיות טוב יותר?",
|
||||||
|
"Drop image to upload": "גרור תמונה להעלאה",
|
||||||
|
|
||||||
|
// --- Aria Labels ---
|
||||||
|
"breadcrumb": "ניווט",
|
||||||
|
"toggle menu": "החלפת תפריט",
|
||||||
|
"Instance settings": "הגדרות מופע",
|
||||||
|
"Scroll to bottom": "גלול למטה",
|
||||||
|
"Change project color": "שנה צבע פרויקט",
|
||||||
|
"Zoom in": "הגדל",
|
||||||
|
"Zoom out": "הקטן",
|
||||||
|
"Fit chart to screen": "התאם תרשים למסך"
|
||||||
|
};
|
||||||
|
|
||||||
|
// =========================================================================
|
||||||
|
// TRANSLATION ENGINE
|
||||||
|
// =========================================================================
|
||||||
|
|
||||||
|
// Build a reverse lookup for performance: lowercase -> original key
|
||||||
|
const lowerMap = {};
|
||||||
|
for (const key in T) {
|
||||||
|
lowerMap[key.toLowerCase()] = key;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Translate a text string if a translation exists.
|
||||||
|
* Uses exact match first, then case-insensitive.
|
||||||
|
*/
|
||||||
|
function translate(text) {
|
||||||
|
const trimmed = text.trim();
|
||||||
|
if (!trimmed) return null;
|
||||||
|
// Exact match
|
||||||
|
if (T[trimmed] !== undefined) return T[trimmed];
|
||||||
|
// Case-insensitive match
|
||||||
|
const lk = trimmed.toLowerCase();
|
||||||
|
if (lowerMap[lk]) return T[lowerMap[lk]];
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if a node is likely user-generated content (should NOT be translated).
|
||||||
|
* This includes agent names, issue titles in dynamic lists, etc.
|
||||||
|
*/
|
||||||
|
function isUserContent(node) {
|
||||||
|
let el = node.parentElement;
|
||||||
|
while (el) {
|
||||||
|
// Skip elements with contenteditable (editors)
|
||||||
|
if (el.contentEditable === "true") return true;
|
||||||
|
// Skip code blocks
|
||||||
|
const tag = el.tagName;
|
||||||
|
if (tag === "CODE" || tag === "PRE") return true;
|
||||||
|
// Skip markdown rendered content body (but not headings/labels)
|
||||||
|
if (el.classList && el.classList.contains("paperclip-markdown")) return true;
|
||||||
|
// Skip elements explicitly marked as user content
|
||||||
|
if (el.dataset && el.dataset.noTranslate === "true") return true;
|
||||||
|
el = el.parentElement;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Walk all text nodes under a root and translate them.
|
||||||
|
*/
|
||||||
|
function translateTextNodes(root) {
|
||||||
|
const walker = document.createTreeWalker(
|
||||||
|
root,
|
||||||
|
NodeFilter.SHOW_TEXT,
|
||||||
|
null
|
||||||
|
);
|
||||||
|
let node;
|
||||||
|
while ((node = walker.nextNode())) {
|
||||||
|
if (isUserContent(node)) continue;
|
||||||
|
const original = node.nodeValue;
|
||||||
|
const translated = translate(original);
|
||||||
|
if (translated !== null && translated !== original) {
|
||||||
|
node.nodeValue = translated;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Translate placeholder and aria-label attributes.
|
||||||
|
*/
|
||||||
|
function translateAttributes(root) {
|
||||||
|
// Placeholders
|
||||||
|
const inputs = root.querySelectorAll("input[placeholder], textarea[placeholder]");
|
||||||
|
inputs.forEach(function (el) {
|
||||||
|
const t = translate(el.placeholder);
|
||||||
|
if (t) el.placeholder = t;
|
||||||
|
});
|
||||||
|
|
||||||
|
// aria-labels
|
||||||
|
const ariaEls = root.querySelectorAll("[aria-label]");
|
||||||
|
ariaEls.forEach(function (el) {
|
||||||
|
const t = translate(el.getAttribute("aria-label"));
|
||||||
|
if (t) el.setAttribute("aria-label", t);
|
||||||
|
});
|
||||||
|
|
||||||
|
// title attributes
|
||||||
|
const titleEls = root.querySelectorAll("[title]");
|
||||||
|
titleEls.forEach(function (el) {
|
||||||
|
const t = translate(el.getAttribute("title"));
|
||||||
|
if (t) el.setAttribute("title", t);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Full translation pass on the entire document.
|
||||||
|
*/
|
||||||
|
function translateAll() {
|
||||||
|
translateTextNodes(document.body);
|
||||||
|
translateAttributes(document.body);
|
||||||
|
// Translate page title
|
||||||
|
if (document.title) {
|
||||||
|
const t = translate(document.title);
|
||||||
|
if (t) document.title = t;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// =========================================================================
|
||||||
|
// MUTATION OBSERVER - catch route changes and dynamic content
|
||||||
|
// =========================================================================
|
||||||
|
let translateTimer = null;
|
||||||
|
|
||||||
|
function scheduleTranslation() {
|
||||||
|
if (translateTimer) return;
|
||||||
|
translateTimer = setTimeout(function () {
|
||||||
|
translateTimer = null;
|
||||||
|
translateAll();
|
||||||
|
}, 50);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Observe #root for changes (React renders here)
|
||||||
|
function startObserver() {
|
||||||
|
const root = document.getElementById("root");
|
||||||
|
if (!root) return;
|
||||||
|
|
||||||
|
const observer = new MutationObserver(function (mutations) {
|
||||||
|
let hasTextChange = false;
|
||||||
|
for (let i = 0; i < mutations.length; i++) {
|
||||||
|
const m = mutations[i];
|
||||||
|
if (m.type === "childList" && m.addedNodes.length > 0) {
|
||||||
|
hasTextChange = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (m.type === "characterData") {
|
||||||
|
hasTextChange = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (hasTextChange) {
|
||||||
|
scheduleTranslation();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
observer.observe(root, {
|
||||||
|
childList: true,
|
||||||
|
subtree: true,
|
||||||
|
characterData: true
|
||||||
|
});
|
||||||
|
|
||||||
|
// Also observe body for Radix portals (dialogs, tooltips, dropdowns)
|
||||||
|
const bodyObserver = new MutationObserver(function (mutations) {
|
||||||
|
for (let i = 0; i < mutations.length; i++) {
|
||||||
|
const m = mutations[i];
|
||||||
|
if (m.type === "childList") {
|
||||||
|
for (let j = 0; j < m.addedNodes.length; j++) {
|
||||||
|
const node = m.addedNodes[j];
|
||||||
|
if (node.nodeType === 1 && node !== root) {
|
||||||
|
translateTextNodes(node);
|
||||||
|
translateAttributes(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
bodyObserver.observe(document.body, {
|
||||||
|
childList: true,
|
||||||
|
subtree: false
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// =========================================================================
|
||||||
|
// INIT
|
||||||
|
// =========================================================================
|
||||||
|
function init() {
|
||||||
|
// Wait for React to render
|
||||||
|
setTimeout(function () {
|
||||||
|
translateAll();
|
||||||
|
startObserver();
|
||||||
|
}, 300);
|
||||||
|
|
||||||
|
// Additional pass after longer delay for lazy-loaded content
|
||||||
|
setTimeout(translateAll, 1500);
|
||||||
|
setTimeout(translateAll, 4000);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Start when DOM is ready
|
||||||
|
if (document.readyState === "loading") {
|
||||||
|
document.addEventListener("DOMContentLoaded", init);
|
||||||
|
} else {
|
||||||
|
init();
|
||||||
|
}
|
||||||
|
})();
|
||||||
@@ -30,4 +30,4 @@ echo "Hebrew RTL patch applied successfully"
|
|||||||
echo "Patched files:"
|
echo "Patched files:"
|
||||||
echo " - $UI_DIR/index.html"
|
echo " - $UI_DIR/index.html"
|
||||||
echo " - $UI_DIR/assets/rtl-override.css"
|
echo " - $UI_DIR/assets/rtl-override.css"
|
||||||
echo " - $UI_DIR/assets/translate-he.js"
|
echo " - $UI_DIR/assets/translate-he.js"
|
||||||
|
|||||||
Reference in New Issue
Block a user