@beyondwork/docx-react-component 1.0.369 → 1.0.370

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.
@@ -3169,7 +3169,97 @@ var DEFAULT_CHROME_STRINGS = {
3169
3169
  modeEditDisabledReason: "Editing is not available in this document.",
3170
3170
  typingOffNoticeTitle: "Typing is off in review",
3171
3171
  typingOffNoticeDetail: "Use Suggest change to propose an edit.",
3172
- typingOffNoticeSuggestingDetail: "Changes are made as suggestions."
3172
+ typingOffNoticeSuggestingDetail: "Changes are made as suggestions.",
3173
+ ribbonTabsLabel: "Ribbon tabs",
3174
+ expandRibbonLabel: "Expand ribbon",
3175
+ collapseRibbonLabel: "Collapse ribbon",
3176
+ analyticsTabBodyLabel: "Analytics tab body",
3177
+ analyticsUnavailable: "Analytics unavailable",
3178
+ reviewTabBodyLabel: "Review tab body",
3179
+ workflowTabBodyLabel: "Workflow tab body",
3180
+ notAvailableCommandHandler: "Not available: command handler not supplied by the toolbar host.",
3181
+ scopeBreakdownLabel: "Scope breakdown",
3182
+ commandPaletteLabel: "Open command palette",
3183
+ toggleAnalyticsLabel: "Toggle analytics",
3184
+ customScopeLabel: "Custom scope",
3185
+ customScopeNameLabel: "Custom scope name",
3186
+ closeCustomScopeDialogLabel: "Close custom scope dialog",
3187
+ addCommentLabel: "Add comment",
3188
+ trackedChangesLabel: "Track Changes",
3189
+ trackedChangesOnLabel: "Tracking on",
3190
+ trackedChangesOffLabel: "Tracking off",
3191
+ trackedChangesOnTitle: "Tracking on: new edits are recorded as redlines",
3192
+ trackedChangesOffTitle: "Tracking off: new edits are applied directly",
3193
+ showTrackedChangesSidebarLabel: "Show tracked changes in sidebar",
3194
+ showCommentsSidebarLabel: "Show comments in sidebar",
3195
+ trackedChangesPanelLabel: "Tracked changes panel",
3196
+ commentsPanelLabel: "Comments panel",
3197
+ compareLabel: "Compare",
3198
+ compareDocumentLabel: "Compare document",
3199
+ compareWithAnotherDocumentLabel: "Compare with another document",
3200
+ chooseDocumentToCompareLabel: "Choose document to compare",
3201
+ moreLabel: "More",
3202
+ pagesLabel: "Pages",
3203
+ charsLabel: "Chars",
3204
+ exportLabel: "Export",
3205
+ blockedLabel: "Blocked",
3206
+ readyLabel: "Ready",
3207
+ itemsLabel: "Items",
3208
+ changesLabel: "Changes",
3209
+ commentsLabel: "Comments",
3210
+ opaqueLabel: "Opaque",
3211
+ scopesLabel: "Scopes",
3212
+ tasksLabel: "Tasks",
3213
+ approvalsLabel: "Approvals",
3214
+ analyticsLabel: "Analytics",
3215
+ homeTabLabel: "Home",
3216
+ insertTabLabel: "Insert",
3217
+ layoutTabLabel: "Layout",
3218
+ reviewTabLabel: "Review",
3219
+ workflowTabLabel: "Workflow",
3220
+ defaultDocumentTitle: "Document",
3221
+ defaultWordmark: "COMPOSER",
3222
+ resolveBlockersAction: "Resolve blockers",
3223
+ reviewPendingChangesAction: "Review pending changes",
3224
+ openCommentThreadAction: "Open comment thread",
3225
+ documentReadyAction: "Document ready",
3226
+ documentGroupLabel: "Document",
3227
+ reviewGroupLabel: "Review",
3228
+ riskGroupLabel: "Risk",
3229
+ workflowGroupLabel: "Workflow",
3230
+ scopesGroupLabel: "Scopes",
3231
+ toolsGroupLabel: "Tools",
3232
+ nextGroupLabel: "Next",
3233
+ savedLabel: "Saved",
3234
+ unsavedLabel: "Unsaved",
3235
+ exportBlockedLabel: "Export blocked",
3236
+ pageAnchoredStoriesNotShownLabel: "Page-anchored stories not shown",
3237
+ trackChangesAuthoringLabel: "Track changes authoring",
3238
+ zoomControlsLabel: "Zoom controls",
3239
+ zoomOutLabel: "Zoom out",
3240
+ zoomLevelLabel: "Zoom level",
3241
+ zoomInLabel: "Zoom in",
3242
+ workspaceViewLabel: "Workspace view",
3243
+ canvasViewLabel: "Canvas view",
3244
+ pageViewLabel: "Page view",
3245
+ markupDisplayLabel: "Markup display",
3246
+ trackingOnDetail: "Tracking on: new typing, insertions, deletions, and formatting changes become redlines.",
3247
+ trackingOffDetail: "Tracking off: new edits are applied directly. Existing markup display is controlled separately.",
3248
+ workflowScopeControlsLabel: "Workflow scope controls",
3249
+ createCustomWorkflowScopeLabel: "Create custom workflow scope",
3250
+ customScopeModeInputLabel: "Custom scope mode",
3251
+ customScopeColorInputLabel: "Custom scope color",
3252
+ scopeColorPlaceholder: "#64748b",
3253
+ metadataKeyPlaceholderLabel: "Key",
3254
+ metadataValuePlaceholderLabel: "Value",
3255
+ customLabel: "Custom",
3256
+ nameLabel: "Name",
3257
+ modeLabel: "Mode",
3258
+ colorLabel: "Color",
3259
+ metadataLabelText: "Metadata",
3260
+ addLabel: "Add",
3261
+ cancelLabel: "Cancel",
3262
+ createLabel: "Create"
3173
3263
  };
3174
3264
 
3175
3265
  // src/ui-tailwind/i18n/chrome-strings.tsx
@@ -40449,6 +40539,7 @@ var CUSTOM_SCOPE_COLOR_SWATCHES = [
40449
40539
  "#0891b2"
40450
40540
  ];
40451
40541
  function TwScopePostureMenu(props) {
40542
+ const strings = useChromeStrings();
40452
40543
  const [customOpen, setCustomOpen] = import_react5.default.useState(false);
40453
40544
  const iconOnly = props.responsiveTier === "mobile" || props.responsiveTier === "compact";
40454
40545
  return /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(
@@ -40456,8 +40547,9 @@ function TwScopePostureMenu(props) {
40456
40547
  {
40457
40548
  className: `relative flex min-w-0 items-center ${iconOnly ? "gap-px" : "gap-1"}`,
40458
40549
  "data-testid": props["data-testid"] ?? "workflow-scope-palette",
40550
+ "data-chrome-unit-id": "chrome.ribbon",
40459
40551
  "data-ribbon-control": "direct-scope-palette",
40460
- "aria-label": "Workflow scope controls",
40552
+ "aria-label": strings.workflowScopeControlsLabel,
40461
40553
  role: "group",
40462
40554
  children: [
40463
40555
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { className: "flex shrink-0 items-center gap-px", children: SCOPE_POSTURE_MENU_ENTRIES.map((entry) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
@@ -40484,9 +40576,9 @@ function TwScopePostureMenu(props) {
40484
40576
  "button",
40485
40577
  {
40486
40578
  type: "button",
40487
- "aria-label": "Create custom workflow scope",
40579
+ "aria-label": strings.createCustomWorkflowScopeLabel,
40488
40580
  "aria-expanded": customOpen,
40489
- title: "Custom scope",
40581
+ title: strings.customScopeLabel,
40490
40582
  disabled: !props.onCreateCustomScope,
40491
40583
  onMouseDown: preserveEditorSelectionMouseDown,
40492
40584
  onClick: () => setCustomOpen((value) => !value),
@@ -40498,7 +40590,7 @@ function TwScopePostureMenu(props) {
40498
40590
  "data-label-visibility": iconOnly ? "icon-only" : "text",
40499
40591
  children: [
40500
40592
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(TwGlyphIcon, { name: "plus", className: "h-3.5 w-3.5 text-accent" }),
40501
- iconOnly ? null : /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { children: "Custom" })
40593
+ iconOnly ? null : /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { children: strings.customLabel })
40502
40594
  ]
40503
40595
  }
40504
40596
  ),
@@ -40514,6 +40606,7 @@ function TwScopePostureMenu(props) {
40514
40606
  );
40515
40607
  }
40516
40608
  function CustomScopeDialog(props) {
40609
+ const strings = useChromeStrings();
40517
40610
  const [mode, setMode] = import_react5.default.useState("suggest");
40518
40611
  const [color, setColor] = import_react5.default.useState(CUSTOM_SCOPE_COLOR_SWATCHES[0]);
40519
40612
  const [metadataRows, setMetadataRows] = import_react5.default.useState([0]);
@@ -40559,12 +40652,12 @@ function CustomScopeDialog(props) {
40559
40652
  },
40560
40653
  children: [
40561
40654
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "flex items-center justify-between gap-2", children: [
40562
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-semibold text-[var(--ink-primary)]", children: "Custom scope" }),
40655
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-semibold text-[var(--ink-primary)]", children: strings.customScopeLabel }),
40563
40656
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
40564
40657
  "button",
40565
40658
  {
40566
40659
  type: "button",
40567
- "aria-label": "Close custom scope dialog",
40660
+ "aria-label": strings.closeCustomScopeDialogLabel,
40568
40661
  onMouseDown: preserveEditorSelectionMouseDown,
40569
40662
  onClick: props.onClose,
40570
40663
  className: ds38IconButtonClass,
@@ -40573,19 +40666,19 @@ function CustomScopeDialog(props) {
40573
40666
  )
40574
40667
  ] }),
40575
40668
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("label", { className: "grid gap-1 font-medium text-[var(--ink-secondary)]", children: [
40576
- "Name",
40669
+ strings.nameLabel,
40577
40670
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
40578
40671
  "input",
40579
40672
  {
40580
40673
  autoFocus: true,
40581
- "aria-label": "Custom scope name",
40674
+ "aria-label": strings.customScopeNameLabel,
40582
40675
  name: "scope-label",
40583
40676
  className: ds38SmallInputClass
40584
40677
  }
40585
40678
  )
40586
40679
  ] }),
40587
- /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "grid gap-1", role: "group", "aria-label": "Custom scope mode", children: [
40588
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-medium text-[var(--ink-secondary)]", children: "Mode" }),
40680
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "grid gap-1", role: "group", "aria-label": strings.customScopeModeInputLabel, children: [
40681
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-medium text-[var(--ink-secondary)]", children: strings.modeLabel }),
40589
40682
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { className: "flex flex-wrap gap-1", children: ["edit", "suggest", "comment", "view"].map((entry) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
40590
40683
  "button",
40591
40684
  {
@@ -40606,8 +40699,8 @@ function CustomScopeDialog(props) {
40606
40699
  entry
40607
40700
  )) })
40608
40701
  ] }),
40609
- /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "grid gap-1", role: "group", "aria-label": "Custom scope color", children: [
40610
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-medium text-[var(--ink-secondary)]", children: "Color" }),
40702
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "grid gap-1", role: "group", "aria-label": strings.customScopeColorInputLabel, children: [
40703
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-medium text-[var(--ink-secondary)]", children: strings.colorLabel }),
40611
40704
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "flex items-center gap-1", children: [
40612
40705
  CUSTOM_SCOPE_COLOR_SWATCHES.map((swatch) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
40613
40706
  "button",
@@ -40628,9 +40721,9 @@ function CustomScopeDialog(props) {
40628
40721
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
40629
40722
  "input",
40630
40723
  {
40631
- "aria-label": "Custom scope color",
40724
+ "aria-label": strings.customScopeColorInputLabel,
40632
40725
  name: "scope-color",
40633
- placeholder: "#64748b",
40726
+ placeholder: strings.scopeColorPlaceholder,
40634
40727
  className: `${ds38SmallInputClass} w-24`
40635
40728
  }
40636
40729
  )
@@ -40638,7 +40731,7 @@ function CustomScopeDialog(props) {
40638
40731
  ] }),
40639
40732
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "grid gap-1", children: [
40640
40733
  /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "flex items-center justify-between", children: [
40641
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-medium text-[var(--ink-secondary)]", children: "Metadata" }),
40734
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "font-medium text-[var(--ink-secondary)]", children: strings.metadataLabelText }),
40642
40735
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
40643
40736
  "button",
40644
40737
  {
@@ -40646,7 +40739,7 @@ function CustomScopeDialog(props) {
40646
40739
  onMouseDown: preserveEditorSelectionMouseDown,
40647
40740
  onClick: () => setMetadataRows((rows) => [...rows, Date.now()]),
40648
40741
  className: `${ds38TextButtonClass} h-6 px-1.5 text-[10px] text-[var(--accent-primary)]`,
40649
- children: "Add"
40742
+ children: strings.addLabel
40650
40743
  }
40651
40744
  )
40652
40745
  ] }),
@@ -40656,7 +40749,7 @@ function CustomScopeDialog(props) {
40656
40749
  {
40657
40750
  "aria-label": `Metadata key ${index + 1}`,
40658
40751
  name: "metadata-key",
40659
- placeholder: "Key",
40752
+ placeholder: strings.metadataKeyPlaceholderLabel,
40660
40753
  className: ds38SmallInputClass
40661
40754
  }
40662
40755
  ),
@@ -40665,7 +40758,7 @@ function CustomScopeDialog(props) {
40665
40758
  {
40666
40759
  "aria-label": `Metadata value ${index + 1}`,
40667
40760
  name: "metadata-value",
40668
- placeholder: "Value",
40761
+ placeholder: strings.metadataValuePlaceholderLabel,
40669
40762
  className: ds38SmallInputClass
40670
40763
  }
40671
40764
  ),
@@ -40698,7 +40791,7 @@ function CustomScopeDialog(props) {
40698
40791
  onMouseDown: preserveEditorSelectionMouseDown,
40699
40792
  onClick: props.onClose,
40700
40793
  className: ds38TextButtonClass,
40701
- children: "Cancel"
40794
+ children: strings.cancelLabel
40702
40795
  }
40703
40796
  ),
40704
40797
  /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
@@ -40707,7 +40800,7 @@ function CustomScopeDialog(props) {
40707
40800
  type: "submit",
40708
40801
  disabled: pending || !props.onCreate,
40709
40802
  className: `h-7 rounded-[var(--r-2)] bg-[var(--accent-primary)] px-2 text-[length:var(--tx-xs)] font-semibold text-white disabled:cursor-not-allowed disabled:opacity-40 ${ds38ControlFocusClass}`,
40710
- children: "Create"
40803
+ children: strings.createLabel
40711
40804
  }
40712
40805
  )
40713
40806
  ] })
@@ -40887,6 +40980,7 @@ function toneClass(tone) {
40887
40980
  // src/ui-tailwind/toolbar/tw-role-action-region.tsx
40888
40981
  var import_jsx_runtime8 = require("react/jsx-runtime");
40889
40982
  function TwRoleActionRegion(props) {
40983
+ const strings = useChromeStrings();
40890
40984
  const responsiveTier = props.responsiveTier ?? (props.compactMode ? "compact" : "standard");
40891
40985
  const order = resolveRoleActionOrder(props.role, props.chromeMode);
40892
40986
  const inlineIds = [];
@@ -40922,6 +41016,7 @@ function TwRoleActionRegion(props) {
40922
41016
  "div",
40923
41017
  {
40924
41018
  className: "flex min-w-0 shrink-0 items-stretch",
41019
+ "data-chrome-unit-id": "chrome.ribbon",
40925
41020
  "data-testid": props["data-testid"] ?? `role-action-region-${props.chromeMode ?? props.role}`,
40926
41021
  "data-role": props.role,
40927
41022
  "data-mode": props.chromeMode,
@@ -40938,7 +41033,7 @@ function TwRoleActionRegion(props) {
40938
41033
  },
40939
41034
  id
40940
41035
  )) }, group2.key)),
40941
- overflowIds.length > 0 ? /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TwRibbonGroup, { label: "More", children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(RoleActionOverflow, { ids: overflowIds, props }) }) : null
41036
+ overflowIds.length > 0 ? /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TwRibbonGroup, { label: strings.moreLabel, children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(RoleActionOverflow, { ids: overflowIds, props }) }) : null
40942
41037
  ]
40943
41038
  }
40944
41039
  );
@@ -41088,6 +41183,7 @@ function roleOverflowLabel(role) {
41088
41183
  }
41089
41184
  function RoleActionButton(arg) {
41090
41185
  const { id, props, responsiveTier } = arg;
41186
+ const strings = useChromeStrings();
41091
41187
  const hideText = shouldUseIconOnlyRoleAction(id, responsiveTier);
41092
41188
  const reviewQueueTotal = props.reviewQueue?.totalCount ?? 0;
41093
41189
  const adjudicationProtected = props.capabilities?.adjudicationBlockedByProtection ?? false;
@@ -41099,7 +41195,7 @@ function RoleActionButton(arg) {
41099
41195
  "button",
41100
41196
  {
41101
41197
  type: "button",
41102
- "aria-label": "Add comment",
41198
+ "aria-label": strings.addCommentLabel,
41103
41199
  disabled: !props.canAddComment || !props.onAddComment,
41104
41200
  onMouseDown: preserveEditorSelectionMouseDown,
41105
41201
  onClick: props.onAddComment,
@@ -41108,7 +41204,7 @@ function RoleActionButton(arg) {
41108
41204
  children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TwGlyphIcon, { name: "comment", className: "h-3.5 w-3.5" })
41109
41205
  }
41110
41206
  ) }),
41111
- /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Portal, { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Content, { className: ds38TooltipClass, sideOffset: 6, children: "Add comment" }) })
41207
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Portal, { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Content, { className: ds38TooltipClass, sideOffset: 6, children: strings.addCommentLabel }) })
41112
41208
  ] });
41113
41209
  case "review-compare-document":
41114
41210
  return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
@@ -41119,7 +41215,7 @@ function RoleActionButton(arg) {
41119
41215
  }
41120
41216
  );
41121
41217
  case "review-track-changes-toggle": {
41122
- const trackChangesLabel = "Track Changes";
41218
+ const trackChangesLabel = strings.trackedChangesLabel;
41123
41219
  const trackedChangesAuthoringEnabled = props.trackedChangesAuthoringEnabled ?? false;
41124
41220
  const onTrackedChangesAuthoringChange = props.onTrackedChangesAuthoringChange ?? props.onShowTrackedChangesChange;
41125
41221
  const trackChangesTooltip = trackedChangesAuthoringEnabled ? "Tracking on: new typing, insertions, deletions, and formatting changes become redlines." : "Tracking off: new edits are applied directly. Existing markup display is controlled in the status bar.";
@@ -41132,7 +41228,7 @@ function RoleActionButton(arg) {
41132
41228
  "aria-label": trackChangesLabel,
41133
41229
  disabled: props.capabilities ? !sessionCanTrackChangesAuthoring(props.capabilities) : false,
41134
41230
  onMouseDown: preserveEditorSelectionMouseDown,
41135
- title: trackedChangesAuthoringEnabled ? "Tracking on: new edits are recorded as redlines" : "Tracking off: new edits are applied directly",
41231
+ title: trackedChangesAuthoringEnabled ? strings.trackedChangesOnTitle : strings.trackedChangesOffTitle,
41136
41232
  className: [
41137
41233
  "inline-flex h-6 items-center justify-center gap-1 rounded-[var(--radius-sm)] px-2",
41138
41234
  "text-[length:var(--text-xs)] font-medium text-[var(--ink-secondary)]",
@@ -41146,7 +41242,7 @@ function RoleActionButton(arg) {
41146
41242
  "data-testid": "role-review-track-changes-toggle",
41147
41243
  children: [
41148
41244
  /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TwGlyphIcon, { name: "edit", className: "h-3.5 w-3.5" }),
41149
- /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { children: trackedChangesAuthoringEnabled ? "Tracking on" : "Tracking off" })
41245
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { children: trackedChangesAuthoringEnabled ? strings.trackedChangesOnLabel : strings.trackedChangesOffLabel })
41150
41246
  ]
41151
41247
  }
41152
41248
  ) }),
@@ -41159,7 +41255,7 @@ function RoleActionButton(arg) {
41159
41255
  "button",
41160
41256
  {
41161
41257
  type: "button",
41162
- "aria-label": "Show tracked changes in sidebar",
41258
+ "aria-label": strings.showTrackedChangesSidebarLabel,
41163
41259
  disabled: !props.onReviewSidebarTrackedChanges,
41164
41260
  onMouseDown: preserveEditorSelectionMouseDown,
41165
41261
  onClick: props.onReviewSidebarTrackedChanges,
@@ -41168,7 +41264,7 @@ function RoleActionButton(arg) {
41168
41264
  children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TwGlyphIcon, { name: "diff", className: "h-3.5 w-3.5" })
41169
41265
  }
41170
41266
  ) }),
41171
- /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Portal, { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Content, { className: ds38TooltipClass, sideOffset: 6, children: "Tracked changes panel" }) })
41267
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Portal, { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Content, { className: ds38TooltipClass, sideOffset: 6, children: strings.trackedChangesPanelLabel }) })
41172
41268
  ] });
41173
41269
  case "comments-panel":
41174
41270
  return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(Tooltip.Root, { children: [
@@ -41176,7 +41272,7 @@ function RoleActionButton(arg) {
41176
41272
  "button",
41177
41273
  {
41178
41274
  type: "button",
41179
- "aria-label": "Show comments in sidebar",
41275
+ "aria-label": strings.showCommentsSidebarLabel,
41180
41276
  disabled: !props.onReviewSidebarComments,
41181
41277
  onMouseDown: preserveEditorSelectionMouseDown,
41182
41278
  onClick: props.onReviewSidebarComments,
@@ -41185,7 +41281,7 @@ function RoleActionButton(arg) {
41185
41281
  children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TwGlyphIcon, { name: "comment", badge: "alert", className: "h-3.5 w-3.5" })
41186
41282
  }
41187
41283
  ) }),
41188
- /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Portal, { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Content, { className: ds38TooltipClass, sideOffset: 6, children: "Comments panel" }) })
41284
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Portal, { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Tooltip.Content, { className: ds38TooltipClass, sideOffset: 6, children: strings.commentsPanelLabel }) })
41189
41285
  ] });
41190
41286
  case "editor-scope-posture-menu":
41191
41287
  return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
@@ -41545,14 +41641,15 @@ function IconTextButton(arg) {
41545
41641
  );
41546
41642
  }
41547
41643
  function ReviewCompareDocumentButton(props) {
41644
+ const strings = useChromeStrings();
41548
41645
  const inputRef = import_react6.default.useRef(null);
41549
41646
  return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(import_jsx_runtime8.Fragment, { children: [
41550
41647
  /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
41551
41648
  IconTextButton,
41552
41649
  {
41553
41650
  icon: twGlyphIconComponent("diff"),
41554
- text: "Compare",
41555
- ariaLabel: "Compare with another document",
41651
+ text: strings.compareLabel,
41652
+ ariaLabel: strings.compareWithAnotherDocumentLabel,
41556
41653
  disabled: props.disabled,
41557
41654
  onClick: () => inputRef.current?.click(),
41558
41655
  "data-testid": props.testId ?? "role-review-compare-document"
@@ -41565,7 +41662,7 @@ function ReviewCompareDocumentButton(props) {
41565
41662
  type: "file",
41566
41663
  accept: ".docx,application/vnd.openxmlformats-officedocument.wordprocessingml.document",
41567
41664
  className: "sr-only",
41568
- "aria-label": "Choose document to compare",
41665
+ "aria-label": strings.chooseDocumentToCompareLabel,
41569
41666
  disabled: props.disabled,
41570
41667
  onChange: (event) => {
41571
41668
  const file = event.currentTarget.files?.[0];
@@ -41583,14 +41680,15 @@ function ReviewCompareDocumentButton(props) {
41583
41680
  ] });
41584
41681
  }
41585
41682
  function CompareMenuRow(arg) {
41683
+ const strings = useChromeStrings();
41586
41684
  const inputRef = import_react6.default.useRef(null);
41587
41685
  return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(import_jsx_runtime8.Fragment, { children: [
41588
41686
  /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
41589
41687
  MenuRow,
41590
41688
  {
41591
41689
  icon: twGlyphIconComponent("diff"),
41592
- label: "Compare document",
41593
- ariaLabel: "Compare with another document",
41690
+ label: strings.compareDocumentLabel,
41691
+ ariaLabel: strings.compareWithAnotherDocumentLabel,
41594
41692
  disabled: arg.disabled,
41595
41693
  onClick: () => inputRef.current?.click()
41596
41694
  }
@@ -41602,7 +41700,7 @@ function CompareMenuRow(arg) {
41602
41700
  type: "file",
41603
41701
  accept: ".docx,application/vnd.openxmlformats-officedocument.wordprocessingml.document",
41604
41702
  className: "sr-only",
41605
- "aria-label": "Choose document to compare",
41703
+ "aria-label": strings.chooseDocumentToCompareLabel,
41606
41704
  disabled: arg.disabled,
41607
41705
  onChange: (event) => {
41608
41706
  const file = event.currentTarget.files?.[0];
@@ -41701,6 +41799,7 @@ function TwRibbonTab(props) {
41701
41799
  "button",
41702
41800
  {
41703
41801
  type: "button",
41802
+ "data-chrome-unit-id": "chrome.ribbon",
41704
41803
  role: "tab",
41705
41804
  "aria-selected": selected,
41706
41805
  "aria-label": label,
@@ -41738,15 +41837,24 @@ function TwRibbonTab(props) {
41738
41837
 
41739
41838
  // src/ui-tailwind/toolbar/tw-ribbon-tab-strip.tsx
41740
41839
  var import_jsx_runtime11 = require("react/jsx-runtime");
41741
- var TAB_DESCRIPTORS = [
41742
- { id: "home", label: "Home" },
41743
- { id: "insert", label: "Insert" },
41744
- { id: "layout", label: "Layout" },
41745
- { id: "review", label: "Review" },
41746
- { id: "workflow", label: "Workflow" },
41747
- { id: "analytics", label: "Analytics" }
41840
+ var TAB_IDS = [
41841
+ "home",
41842
+ "insert",
41843
+ "layout",
41844
+ "review",
41845
+ "workflow",
41846
+ "analytics"
41748
41847
  ];
41749
41848
  function TwRibbonTabStrip(props) {
41849
+ const strings = useChromeStrings();
41850
+ const tabLabels = {
41851
+ home: strings.homeTabLabel,
41852
+ insert: strings.insertTabLabel,
41853
+ layout: strings.layoutTabLabel,
41854
+ review: strings.reviewTabLabel,
41855
+ workflow: strings.workflowTabLabel,
41856
+ analytics: strings.analyticsLabel
41857
+ };
41750
41858
  const responsiveTier = props.responsiveTier ?? "standard";
41751
41859
  const isMobile = responsiveTier === "mobile";
41752
41860
  const disabledSet = import_react8.default.useMemo(
@@ -41757,6 +41865,7 @@ function TwRibbonTabStrip(props) {
41757
41865
  "div",
41758
41866
  {
41759
41867
  "data-testid": "ribbon-tab-strip",
41868
+ "data-chrome-unit-id": "chrome.ribbon",
41760
41869
  "data-ribbon-layer": "tabs",
41761
41870
  "data-responsive-tier": responsiveTier,
41762
41871
  className: [
@@ -41768,22 +41877,22 @@ function TwRibbonTabStrip(props) {
41768
41877
  "div",
41769
41878
  {
41770
41879
  role: "tablist",
41771
- "aria-label": "Ribbon tabs",
41880
+ "aria-label": strings.ribbonTabsLabel,
41772
41881
  className: [
41773
41882
  "flex min-w-0 shrink items-end gap-0",
41774
41883
  "overflow-x-auto overflow-y-hidden [scrollbar-width:none] [&::-webkit-scrollbar]:hidden"
41775
41884
  ].join(" "),
41776
- children: TAB_DESCRIPTORS.map((tab) => /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(
41885
+ children: TAB_IDS.map((id) => /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(
41777
41886
  TwRibbonTab,
41778
41887
  {
41779
- id: tab.id,
41780
- label: tab.label,
41781
- selected: tab.id === props.activeTab,
41782
- disabled: disabledSet.has(tab.id),
41888
+ id,
41889
+ label: tabLabels[id],
41890
+ selected: id === props.activeTab,
41891
+ disabled: disabledSet.has(id),
41783
41892
  responsiveTier,
41784
41893
  onSelect: props.onTabChange
41785
41894
  },
41786
- tab.id
41895
+ id
41787
41896
  ))
41788
41897
  }
41789
41898
  ),
@@ -41795,10 +41904,10 @@ function TwRibbonTabStrip(props) {
41795
41904
  type: "button",
41796
41905
  "data-testid": "ribbon-collapse-toggle",
41797
41906
  "aria-pressed": props.collapsed,
41798
- "aria-label": props.collapsed ? "Expand ribbon" : "Collapse ribbon",
41907
+ "aria-label": props.collapsed ? strings.expandRibbonLabel : strings.collapseRibbonLabel,
41799
41908
  onClick: props.onCollapseToggle,
41800
41909
  "data-label-visibility": isMobile ? "icon-only" : "text",
41801
- title: isMobile ? props.collapsed ? "Expand ribbon" : "Collapse ribbon" : void 0,
41910
+ title: isMobile ? props.collapsed ? strings.expandRibbonLabel : strings.collapseRibbonLabel : void 0,
41802
41911
  className: [
41803
41912
  "inline-flex h-6 items-center rounded text-[length:var(--text-xs)] text-[var(--ink-secondary)]",
41804
41913
  "transition-colors duration-[var(--t-fast)] hover:bg-[var(--bg-hover)] hover:text-[var(--ink-primary)]",
@@ -41820,15 +41929,17 @@ function TwRibbonTabStrip(props) {
41820
41929
  // src/ui-tailwind/toolbar/tw-ribbon-tab-body-analytics.tsx
41821
41930
  var import_jsx_runtime12 = require("react/jsx-runtime");
41822
41931
  function TwRibbonTabBodyAnalytics(props) {
41932
+ const strings = useChromeStrings();
41823
41933
  return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
41824
41934
  "div",
41825
41935
  {
41826
41936
  "data-testid": "ribbon-tab-body-analytics",
41937
+ "data-chrome-unit-id": "chrome.ribbon",
41827
41938
  "data-ribbon-tab-body": "analytics",
41828
41939
  "data-ribbon-body-density": "standard",
41829
- "aria-label": "Analytics tab body",
41940
+ "aria-label": strings.analyticsTabBodyLabel,
41830
41941
  className: "flex h-full min-w-0 flex-nowrap items-center overflow-hidden px-0 py-0",
41831
- children: props.children ?? /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { className: "px-3 text-[length:var(--text-xs)] text-tertiary", children: "Analytics unavailable" })
41942
+ children: props.children ?? /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { className: "px-3 text-[length:var(--text-xs)] text-tertiary", children: strings.analyticsUnavailable })
41832
41943
  }
41833
41944
  );
41834
41945
  }
@@ -41846,12 +41957,14 @@ var GROUP_LABEL = {
41846
41957
  symbol: "Symbol"
41847
41958
  };
41848
41959
  function TwRibbonTabBodyInsert(props) {
41960
+ const strings = useChromeStrings();
41849
41961
  const entries = filterRegistryByTab("insert");
41850
41962
  const byGroup = groupEntriesByGroup(entries);
41851
41963
  return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
41852
41964
  "div",
41853
41965
  {
41854
41966
  "data-testid": "ribbon-tab-body-insert",
41967
+ "data-chrome-unit-id": "chrome.ribbon",
41855
41968
  "data-ribbon-tab-body": "insert",
41856
41969
  "data-ribbon-body-density": "compact",
41857
41970
  className: "flex h-full min-w-0 flex-nowrap items-center gap-1 overflow-hidden px-3 py-0",
@@ -41862,7 +41975,7 @@ function TwRibbonTabBodyInsert(props) {
41862
41975
  "data-testid": `ribbon-tab-body-insert-entry-${id}`,
41863
41976
  "data-ribbon-entry-id": id,
41864
41977
  disabled: true,
41865
- title: "Not available: command handler not supplied by the toolbar host.",
41978
+ title: strings.notAvailableCommandHandler,
41866
41979
  className: "inline-flex h-6 items-center rounded px-1.5 text-[length:var(--text-xs)] text-[var(--ink-secondary)] opacity-50",
41867
41980
  children: labelForEntry(id)
41868
41981
  },
@@ -41902,6 +42015,7 @@ var GROUP_LABEL2 = {
41902
42015
  ruler: "Ruler"
41903
42016
  };
41904
42017
  function TwRibbonTabBodyLayout(props) {
42018
+ const strings = useChromeStrings();
41905
42019
  const entries = filterRegistryByTab("layout");
41906
42020
  const byGroup = {};
41907
42021
  for (const entry of entries) {
@@ -41913,6 +42027,7 @@ function TwRibbonTabBodyLayout(props) {
41913
42027
  "div",
41914
42028
  {
41915
42029
  "data-testid": "ribbon-tab-body-layout",
42030
+ "data-chrome-unit-id": "chrome.ribbon",
41916
42031
  "data-ribbon-tab-body": "layout",
41917
42032
  "data-ribbon-body-density": "compact",
41918
42033
  className: "flex h-full min-w-0 flex-nowrap items-center gap-1 overflow-hidden px-3 py-0",
@@ -41923,7 +42038,7 @@ function TwRibbonTabBodyLayout(props) {
41923
42038
  "data-testid": `ribbon-tab-body-layout-entry-${id}`,
41924
42039
  "data-ribbon-entry-id": id,
41925
42040
  disabled: true,
41926
- title: "Not available: command handler not supplied by the toolbar host.",
42041
+ title: strings.notAvailableCommandHandler,
41927
42042
  className: "inline-flex h-6 items-center rounded px-1.5 text-[length:var(--text-xs)] text-[var(--ink-secondary)] opacity-50",
41928
42043
  children: labelForEntry2(id)
41929
42044
  },
@@ -41944,13 +42059,15 @@ function labelForEntry2(id) {
41944
42059
  // src/ui-tailwind/toolbar/tw-ribbon-tab-body-mode.tsx
41945
42060
  var import_jsx_runtime15 = require("react/jsx-runtime");
41946
42061
  function TwRibbonTabBodyMode(props) {
42062
+ const strings = useChromeStrings();
41947
42063
  return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
41948
42064
  "div",
41949
42065
  {
41950
42066
  "data-testid": `ribbon-tab-body-${props.tab}`,
42067
+ "data-chrome-unit-id": "chrome.ribbon",
41951
42068
  "data-ribbon-tab-body": props.tab,
41952
42069
  "data-ribbon-body-density": "compact",
41953
- "aria-label": "Workflow tab body",
42070
+ "aria-label": strings.workflowTabBodyLabel,
41954
42071
  className: "flex h-full min-w-0 flex-nowrap items-center gap-1 overflow-hidden px-3 py-0",
41955
42072
  children: props.children ?? null
41956
42073
  }
@@ -41960,13 +42077,15 @@ function TwRibbonTabBodyMode(props) {
41960
42077
  // src/ui-tailwind/toolbar/tw-ribbon-tab-body-review.tsx
41961
42078
  var import_jsx_runtime16 = require("react/jsx-runtime");
41962
42079
  function TwRibbonTabBodyReview(props) {
42080
+ const strings = useChromeStrings();
41963
42081
  return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
41964
42082
  "div",
41965
42083
  {
41966
42084
  "data-testid": "ribbon-tab-body-review",
42085
+ "data-chrome-unit-id": "chrome.ribbon",
41967
42086
  "data-ribbon-tab-body": "review",
41968
42087
  "data-ribbon-body-density": "compact",
41969
- "aria-label": "Review tab body",
42088
+ "aria-label": strings.reviewTabBodyLabel,
41970
42089
  className: "flex h-full min-w-0 flex-nowrap items-center gap-1 overflow-hidden px-3 py-0",
41971
42090
  children: props.children ?? null
41972
42091
  }
@@ -42103,6 +42222,7 @@ function TwDisplayModeSelector(props) {
42103
42222
  "button",
42104
42223
  {
42105
42224
  type: "button",
42225
+ "data-chrome-unit-id": "chrome.ribbon",
42106
42226
  disabled: props.disabled,
42107
42227
  "data-testid": props["data-testid"] ?? "display-mode-selector-trigger",
42108
42228
  "data-ribbon-control": "compact-selector",
@@ -42910,6 +43030,7 @@ function TwToolbarIconButton(props) {
42910
43030
  "button",
42911
43031
  {
42912
43032
  type: "button",
43033
+ "data-chrome-unit-id": "chrome.ribbon",
42913
43034
  "aria-label": props.label,
42914
43035
  "aria-pressed": props.active ?? void 0,
42915
43036
  "data-active": props.active ? "true" : void 0,
@@ -46710,6 +46831,11 @@ function TwModePill(props) {
46710
46831
 
46711
46832
  // src/ui-tailwind/toolbar/tw-shell-header.tsx
46712
46833
  var import_jsx_runtime30 = require("react/jsx-runtime");
46834
+ var DEFAULT_SHELL_HEADER_MODES = [
46835
+ { id: "edit", label: DEFAULT_CHROME_STRINGS.modeEditLabel },
46836
+ { id: "review", label: DEFAULT_CHROME_STRINGS.reviewTabLabel },
46837
+ { id: "workflow", label: DEFAULT_CHROME_STRINGS.workflowTabLabel }
46838
+ ];
46713
46839
  var POSTURE_HUES = {
46714
46840
  ready: "var(--sem-success)",
46715
46841
  unsaved: "var(--accent-primary)",
@@ -46717,8 +46843,9 @@ var POSTURE_HUES = {
46717
46843
  blocked: "var(--sem-error)"
46718
46844
  };
46719
46845
  function TwShellHeader(props) {
46720
- const title = props.documentTitle ?? props.brand ?? "Document";
46721
- const wordmark = props.wordmark ?? "COMPOSER";
46846
+ const strings = useChromeStrings();
46847
+ const title = props.documentTitle ?? props.brand ?? strings.defaultDocumentTitle;
46848
+ const wordmark = props.wordmark ?? strings.defaultWordmark;
46722
46849
  const posture = props.posture ?? (props.saveState === "dirty" || props.saveState === "saving" ? "unsaved" : "ready");
46723
46850
  const responsiveTier = props.responsiveTier ?? "wide";
46724
46851
  const atLeastCompact = responsiveTier !== "mobile";
@@ -46831,8 +46958,8 @@ function TwShellHeader(props) {
46831
46958
  type: "button",
46832
46959
  "data-testid": "tw-shell-header__command",
46833
46960
  "data-chrome-command-trigger": "true",
46834
- "aria-label": "Open command palette",
46835
- title: "Open command palette",
46961
+ "aria-label": strings.commandPaletteLabel,
46962
+ title: strings.commandPaletteLabel,
46836
46963
  disabled: props.commandPaletteDisabled,
46837
46964
  onClick: props.onOpenCommandPalette,
46838
46965
  className: "inline-flex h-7 w-7 items-center justify-center rounded text-[var(--ink-secondary)] transition-colors hover:bg-[var(--bg-hover)] hover:text-[var(--ink-primary)] disabled:cursor-not-allowed disabled:opacity-40 focus-visible:outline-none focus-visible:shadow-[var(--shadow-focus)]",
@@ -46852,13 +46979,13 @@ function TwShellHeader(props) {
46852
46979
  {
46853
46980
  type: "button",
46854
46981
  "data-testid": "tw-shell-header__analytics",
46855
- "aria-label": "Toggle analytics",
46982
+ "aria-label": strings.toggleAnalyticsLabel,
46856
46983
  "aria-pressed": props.analyticsActive ?? false,
46857
46984
  onClick: props.onToggleAnalytics,
46858
46985
  className: "inline-flex h-7 items-center gap-1.5 rounded px-2 text-[length:var(--tx-sm)] font-medium text-[var(--ink-secondary)] transition-colors hover:bg-[var(--bg-hover)] hover:text-[var(--ink-primary)] aria-pressed:bg-[var(--accent-soft)] aria-pressed:text-[var(--accent-on-soft)] focus-visible:outline-none focus-visible:shadow-[var(--shadow-focus)]",
46859
46986
  children: [
46860
46987
  /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(TwGlyphIcon, { name: "bar-blocks", className: "h-3.5 w-3.5", "aria-hidden": "true" }),
46861
- /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("span", { className: atLeastStandard ? "inline" : "hidden", children: "Analytics" })
46988
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("span", { className: atLeastStandard ? "inline" : "hidden", children: strings.analyticsLabel })
46862
46989
  ]
46863
46990
  }
46864
46991
  ) : null,
@@ -46926,6 +47053,7 @@ function isSafeShellHref(href) {
46926
47053
  // src/ui-tailwind/toolbar/tw-analytics-ribbon.tsx
46927
47054
  var import_jsx_runtime31 = require("react/jsx-runtime");
46928
47055
  function TwAnalyticsRibbon(props) {
47056
+ const strings = useChromeStrings();
46929
47057
  const commentThreads = props.comments?.threads ?? [];
46930
47058
  const resolvedCommentIds = props.comments?.resolvedCommentIds ?? [];
46931
47059
  const revisions = props.trackedChanges?.revisions ?? [];
@@ -46946,7 +47074,7 @@ function TwAnalyticsRibbon(props) {
46946
47074
  const scopeCount = scopeRailSegments.length;
46947
47075
  const toolCount = props.toolRegistry?.editorActions.length ?? props.toolRegistry?.commandPalette.length ?? 0;
46948
47076
  const state = blocked > 0 ? "blocked" : openComments + pendingChanges + tasks + approvals === 0 ? "empty" : "ready";
46949
- const recentAction = props.contextAnalytics?.nextActions[0]?.label ?? (blocked > 0 ? "Resolve blockers" : pendingChanges > 0 ? "Review pending changes" : openComments > 0 ? "Open comment thread" : "Document ready");
47077
+ const recentAction = props.contextAnalytics?.nextActions[0]?.label ?? (blocked > 0 ? strings.resolveBlockersAction : pendingChanges > 0 ? strings.reviewPendingChangesAction : openComments > 0 ? strings.openCommentThreadAction : strings.documentReadyAction);
46950
47078
  const nextActions = (props.contextAnalytics?.nextActions ?? []).slice(0, 2).map((action) => action.label);
46951
47079
  const visibleNextActions = nextActions.length > 0 ? nextActions : [recentAction];
46952
47080
  return /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(
@@ -46954,34 +47082,35 @@ function TwAnalyticsRibbon(props) {
46954
47082
  {
46955
47083
  className: "flex h-full min-w-0 flex-1 items-center overflow-hidden px-1",
46956
47084
  "data-testid": "tw-analytics-ribbon",
47085
+ "data-chrome-unit-id": "chrome.ribbon",
46957
47086
  "data-region": "rib-analytics",
46958
47087
  "data-analytics-state": state,
46959
47088
  "data-analytics-review-items": totalReviewItems,
46960
47089
  "data-analytics-tool-registry-count": toolCount,
46961
47090
  children: [
46962
- /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: "Document", children: [
46963
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Pages", value: props.pageCount == null ? "..." : String(props.pageCount) }),
46964
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Chars", value: formatCompactNumber(props.documentStats?.storyLength ?? 0) }),
46965
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Export", value: props.exportBlocked ? "Blocked" : "Ready", tone: props.exportBlocked ? "blocked" : "ready" })
47091
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: strings.documentGroupLabel, children: [
47092
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.pagesLabel, value: props.pageCount == null ? "..." : String(props.pageCount) }),
47093
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.charsLabel, value: formatCompactNumber(props.documentStats?.storyLength ?? 0) }),
47094
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.exportLabel, value: props.exportBlocked ? strings.blockedLabel : strings.readyLabel, tone: props.exportBlocked ? "blocked" : "ready" })
46966
47095
  ] }),
46967
- /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: "Review", children: [
46968
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Items", value: String(totalReviewItems), tone: totalReviewItems > 0 ? "attention" : "neutral" }),
46969
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: "Changes", value: pendingChanges, color: "var(--sem-warning)" }),
46970
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: "Comments", value: openComments, color: "var(--markup-comment-ink)" })
47096
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: strings.reviewGroupLabel, children: [
47097
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.itemsLabel, value: String(totalReviewItems), tone: totalReviewItems > 0 ? "attention" : "neutral" }),
47098
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: strings.changesLabel, value: pendingChanges, color: "var(--sem-warning)" }),
47099
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: strings.commentsLabel, value: openComments, color: "var(--markup-comment-ink)" })
46971
47100
  ] }),
46972
- /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: "Risk", children: [
46973
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Opaque", value: String(props.documentStats?.opaqueFragmentCount ?? 0), tone: (props.documentStats?.opaqueFragmentCount ?? 0) > 0 ? "attention" : "neutral" }),
46974
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Blocked", value: String(blocked), tone: blocked > 0 ? "blocked" : "neutral" })
47101
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: strings.riskGroupLabel, children: [
47102
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.opaqueLabel, value: String(props.documentStats?.opaqueFragmentCount ?? 0), tone: (props.documentStats?.opaqueFragmentCount ?? 0) > 0 ? "attention" : "neutral" }),
47103
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.blockedLabel, value: String(blocked), tone: blocked > 0 ? "blocked" : "neutral" })
46975
47104
  ] }),
46976
- /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: "Workflow", children: [
46977
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Scopes", value: String(scopeCount) }),
46978
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: "Tasks", value: tasks, color: "var(--mode-workflow)" }),
46979
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: "Approvals", value: approvals, color: "var(--scope-review-marker)" }),
46980
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: "Blocked", value: blocked, color: "var(--sem-error)" })
47105
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TwRibbonGroup, { label: strings.workflowGroupLabel, children: [
47106
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.scopesLabel, value: String(scopeCount) }),
47107
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: strings.tasksLabel, value: tasks, color: "var(--mode-workflow)" }),
47108
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: strings.approvalsLabel, value: approvals, color: "var(--scope-review-marker)" }),
47109
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(MetricCell, { label: strings.blockedLabel, value: blocked, color: "var(--sem-error)" })
46981
47110
  ] }),
46982
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TwRibbonGroup, { label: "Scopes", children: /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(ScopeBreakdown, { segments: scopeRailSegments }) }),
46983
- toolCount > 0 ? /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TwRibbonGroup, { label: "Tools", children: /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: "Tools", value: String(toolCount) }) }) : null,
46984
- /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TwRibbonGroup, { label: "Next", children: visibleNextActions.slice(0, 2).map((action, index) => /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(
47111
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TwRibbonGroup, { label: strings.scopesGroupLabel, children: /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(ScopeBreakdown, { segments: scopeRailSegments, label: strings.scopeBreakdownLabel }) }),
47112
+ toolCount > 0 ? /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TwRibbonGroup, { label: strings.toolsGroupLabel, children: /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(FactCell, { label: strings.toolsGroupLabel, value: String(toolCount) }) }) : null,
47113
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TwRibbonGroup, { label: strings.nextGroupLabel, children: visibleNextActions.slice(0, 2).map((action, index) => /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(
46985
47114
  "span",
46986
47115
  {
46987
47116
  className: "max-w-28 truncate px-1 text-[length:var(--tx-xs)] font-medium text-[var(--ink-secondary)]",
@@ -47035,7 +47164,7 @@ function ScopeBreakdown(props) {
47035
47164
  "div",
47036
47165
  {
47037
47166
  className: "flex h-2 w-28 overflow-hidden rounded-[var(--r-1)] bg-[var(--bg-muted)]",
47038
- "aria-label": "Scope breakdown",
47167
+ "aria-label": props.label,
47039
47168
  role: "img",
47040
47169
  children: [
47041
47170
  /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(BreakdownSegment, { value: counts.edit, total, color: "var(--scope-edit-marker)" }),
@@ -54350,6 +54479,7 @@ var STATUS_POSTURE_PIP_CLASS = {
54350
54479
  blocked: "bg-[var(--sem-error)]"
54351
54480
  };
54352
54481
  function TwStatusBar(props) {
54482
+ const strings = useChromeStrings();
54353
54483
  const responsiveTier = props.responsiveTier ?? "wide";
54354
54484
  const atLeastCompact = responsiveTier !== "mobile";
54355
54485
  const atLeastStandard = responsiveTier === "standard" || responsiveTier === "wide";
@@ -54359,7 +54489,7 @@ function TwStatusBar(props) {
54359
54489
  const showPosture = segmentVisible("status-save-state");
54360
54490
  const preservationStatusMessage = getPreserveOnlyStatusMessage(props.preserveOnlyCount);
54361
54491
  const savePosture = props.isDirty ? "unsaved" : "ready";
54362
- const saveLabel = props.isDirty ? "Unsaved" : "Saved";
54492
+ const saveLabel = props.isDirty ? strings.unsavedLabel : strings.savedLabel;
54363
54493
  const showExportPosture = showPosture && props.isExportBlocked;
54364
54494
  const showOpenChangesPosture = showPosture && props.changeCount > 0;
54365
54495
  const openChangesLabel = `${props.changeCount} ${props.changeCount === 1 ? "change" : "changes"}`;
@@ -54389,7 +54519,7 @@ function TwStatusBar(props) {
54389
54519
  const showZoomControls = (props.zoomLevel != null || props.onZoomChange) && segmentVisible("status-zoom");
54390
54520
  const trackingEnabled = Boolean(props.trackedChangesAuthoringEnabled);
54391
54521
  const trackingDisabled = props.trackedChangesAuthoringDisabled === true || !props.onTrackedChangesAuthoringChange;
54392
- const trackingTitle = trackingEnabled ? "Tracking on: new typing, insertions, deletions, and formatting changes become redlines." : "Tracking off: new edits are applied directly. Existing markup display is controlled separately.";
54522
+ const trackingTitle = trackingEnabled ? strings.trackingOnDetail : strings.trackingOffDetail;
54393
54523
  const trackingControlTitle = trackingDisabled && props.trackedChangesAuthoringDisabledReason ? props.trackedChangesAuthoringDisabledReason : trackingTitle;
54394
54524
  const statusChromeMode = segmentVisible("status-mode") ? normalizeStatusChromeMode(props.chromeMode) : null;
54395
54525
  const modeLabel = statusChromeMode ? formatStatusChromeModeLabel(statusChromeMode) : null;
@@ -54468,7 +54598,7 @@ function TwStatusBar(props) {
54468
54598
  className: "inline-flex items-center gap-1",
54469
54599
  "data-testid": "status-bar-posture-export",
54470
54600
  "data-posture": "blocked",
54471
- title: "Export blocked",
54601
+ title: strings.exportBlockedLabel,
54472
54602
  children: [
54473
54603
  /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
54474
54604
  "span",
@@ -54477,7 +54607,7 @@ function TwStatusBar(props) {
54477
54607
  className: `h-1.5 w-1.5 shrink-0 rounded-[1px] ${STATUS_POSTURE_PIP_CLASS.blocked}`
54478
54608
  }
54479
54609
  ),
54480
- /* @__PURE__ */ (0, import_jsx_runtime57.jsx)("span", { className: atLeastCompact ? "" : "hidden", children: "Export blocked" })
54610
+ /* @__PURE__ */ (0, import_jsx_runtime57.jsx)("span", { className: atLeastCompact ? "" : "hidden", children: strings.exportBlockedLabel })
54481
54611
  ]
54482
54612
  }
54483
54613
  ) : null,
@@ -54511,7 +54641,7 @@ function TwStatusBar(props) {
54511
54641
  className: "flex shrink-0 items-center overflow-hidden",
54512
54642
  "data-testid": "status-bar-page-anchored-stories",
54513
54643
  "data-chrome-unit-id": "status-page-anchored-stories",
54514
- "aria-label": "Page-anchored stories not shown",
54644
+ "aria-label": strings.pageAnchoredStoriesNotShownLabel,
54515
54645
  title: `${hiddenStoryCount} page-anchored ${hiddenStoryCount === 1 ? "story" : "stories"} (headers, footers, notes) ${hiddenStoryCount === 1 ? "is" : "are"} not shown in this view`,
54516
54646
  children: /* @__PURE__ */ (0, import_jsx_runtime57.jsxs)("span", { className: "inline-flex h-5 items-center gap-1 rounded-[var(--r-2)] px-1.5 text-[var(--text-secondary)]", children: [
54517
54647
  hiddenStoryCount,
@@ -54526,12 +54656,12 @@ function TwStatusBar(props) {
54526
54656
  className: `flex shrink-0 items-center overflow-hidden ${isWide ? "w-[8.75rem]" : atLeastCompact ? "w-[4rem]" : "w-7"}`,
54527
54657
  "data-testid": "status-bar-track-changes",
54528
54658
  "data-chrome-unit-id": "status-track-changes",
54529
- "aria-label": "Track changes authoring",
54659
+ "aria-label": strings.trackChangesAuthoringLabel,
54530
54660
  children: /* @__PURE__ */ (0, import_jsx_runtime57.jsxs)(
54531
54661
  "button",
54532
54662
  {
54533
54663
  type: "button",
54534
- "aria-label": "Track Changes",
54664
+ "aria-label": strings.trackedChangesLabel,
54535
54665
  "aria-pressed": trackingEnabled,
54536
54666
  disabled: trackingDisabled,
54537
54667
  onClick: () => props.onTrackedChangesAuthoringChange?.(!trackingEnabled),
@@ -54568,7 +54698,7 @@ function TwStatusBar(props) {
54568
54698
  className: `shrink-0 items-center gap-1 overflow-hidden ${atLeastStandard ? "flex" : "hidden"} ${isWide ? "w-[8.75rem]" : "w-[4.25rem]"}`,
54569
54699
  "data-testid": "status-bar-markup-mode",
54570
54700
  "data-chrome-unit-id": "status-markup-display",
54571
- "aria-label": "Markup display",
54701
+ "aria-label": strings.markupDisplayLabel,
54572
54702
  children: [
54573
54703
  /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
54574
54704
  "div",
@@ -54705,13 +54835,13 @@ function TwStatusBar(props) {
54705
54835
  className: "flex w-11 shrink-0 items-center gap-px",
54706
54836
  "data-testid": "status-bar-workspace-mode",
54707
54837
  "data-chrome-unit-id": "status-workspace-view",
54708
- "aria-label": "Workspace view",
54838
+ "aria-label": strings.workspaceViewLabel,
54709
54839
  children: [
54710
54840
  /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
54711
54841
  StatusChromeButton,
54712
54842
  {
54713
54843
  active: props.workspace === "canvas",
54714
- ariaLabel: "Canvas view",
54844
+ ariaLabel: strings.canvasViewLabel,
54715
54845
  disabled: !props.onWorkspaceModeChange,
54716
54846
  onClick: () => props.onWorkspaceModeChange?.("canvas"),
54717
54847
  children: /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(TwGlyphIcon, { name: "desktop", className: "h-3 w-3", "aria-hidden": "true" })
@@ -54721,7 +54851,7 @@ function TwStatusBar(props) {
54721
54851
  StatusChromeButton,
54722
54852
  {
54723
54853
  active: props.workspace === "page",
54724
- ariaLabel: "Page view",
54854
+ ariaLabel: strings.pageViewLabel,
54725
54855
  disabled: !props.onWorkspaceModeChange,
54726
54856
  onClick: () => props.onWorkspaceModeChange?.("page"),
54727
54857
  children: /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(TwGlyphIcon, { name: "document", className: "h-3 w-3", "aria-hidden": "true" })
@@ -54741,13 +54871,13 @@ function TwStatusBar(props) {
54741
54871
  ].join(" "),
54742
54872
  "data-testid": "status-bar-zoom",
54743
54873
  "data-chrome-unit-id": "status-zoom",
54744
- "aria-label": "Zoom controls",
54874
+ "aria-label": strings.zoomControlsLabel,
54745
54875
  children: [
54746
54876
  /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
54747
54877
  "button",
54748
54878
  {
54749
54879
  type: "button",
54750
- "aria-label": "Zoom out",
54880
+ "aria-label": strings.zoomOutLabel,
54751
54881
  disabled: !canDecreaseZoom,
54752
54882
  onClick: () => applyZoom(zoomPercent - STATUS_ZOOM_BUTTON_STEP),
54753
54883
  className: [
@@ -54759,7 +54889,7 @@ function TwStatusBar(props) {
54759
54889
  /* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
54760
54890
  "input",
54761
54891
  {
54762
- "aria-label": "Zoom level",
54892
+ "aria-label": strings.zoomLevelLabel,
54763
54893
  type: "range",
54764
54894
  min: Math.min(STATUS_ZOOM_MIN, Math.floor(zoomPercent / STATUS_ZOOM_STEP) * STATUS_ZOOM_STEP),
54765
54895
  max: STATUS_ZOOM_MAX,
@@ -54790,7 +54920,7 @@ function TwStatusBar(props) {
54790
54920
  "button",
54791
54921
  {
54792
54922
  type: "button",
54793
- "aria-label": "Zoom in",
54923
+ "aria-label": strings.zoomInLabel,
54794
54924
  disabled: !canIncreaseZoom,
54795
54925
  onClick: () => applyZoom(zoomPercent + STATUS_ZOOM_BUTTON_STEP),
54796
54926
  className: [