@univerjs/find-replace 1.0.0-insiders.20260809-70eefdd → 1.0.0-rc.0

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.
Files changed (96) hide show
  1. package/LICENSE +176 -0
  2. package/README.md +0 -1
  3. package/lib/cjs/index.js +521 -8
  4. package/lib/cjs/locale/ar-SA.js +7 -1
  5. package/lib/cjs/locale/ca-ES.js +7 -1
  6. package/lib/cjs/locale/de-DE.js +7 -1
  7. package/lib/cjs/locale/en-US.js +7 -1
  8. package/lib/cjs/locale/es-ES.js +7 -1
  9. package/lib/cjs/locale/fa-IR.js +7 -1
  10. package/lib/cjs/locale/fr-FR.js +7 -1
  11. package/lib/cjs/locale/id-ID.js +7 -1
  12. package/lib/cjs/locale/it-IT.js +7 -1
  13. package/lib/cjs/locale/ja-JP.js +7 -1
  14. package/lib/cjs/locale/ko-KR.js +7 -1
  15. package/lib/cjs/locale/pl-PL.js +7 -1
  16. package/lib/cjs/locale/pt-BR.js +7 -1
  17. package/lib/cjs/locale/ru-RU.js +7 -1
  18. package/lib/cjs/locale/sk-SK.js +7 -1
  19. package/lib/cjs/locale/vi-VN.js +7 -1
  20. package/lib/cjs/locale/zh-CN.js +7 -1
  21. package/lib/cjs/locale/zh-HK.js +7 -1
  22. package/lib/cjs/locale/zh-TW.js +7 -1
  23. package/lib/es/index.js +520 -14
  24. package/lib/es/locale/ar-SA.js +7 -1
  25. package/lib/es/locale/ca-ES.js +7 -1
  26. package/lib/es/locale/de-DE.js +7 -1
  27. package/lib/es/locale/en-US.js +7 -1
  28. package/lib/es/locale/es-ES.js +7 -1
  29. package/lib/es/locale/fa-IR.js +7 -1
  30. package/lib/es/locale/fr-FR.js +7 -1
  31. package/lib/es/locale/id-ID.js +7 -1
  32. package/lib/es/locale/it-IT.js +7 -1
  33. package/lib/es/locale/ja-JP.js +7 -1
  34. package/lib/es/locale/ko-KR.js +7 -1
  35. package/lib/es/locale/pl-PL.js +7 -1
  36. package/lib/es/locale/pt-BR.js +7 -1
  37. package/lib/es/locale/ru-RU.js +7 -1
  38. package/lib/es/locale/sk-SK.js +7 -1
  39. package/lib/es/locale/vi-VN.js +7 -1
  40. package/lib/es/locale/zh-CN.js +7 -1
  41. package/lib/es/locale/zh-HK.js +7 -1
  42. package/lib/es/locale/zh-TW.js +7 -1
  43. package/lib/index.css +204 -0
  44. package/lib/index.js +520 -14
  45. package/lib/locale/ar-SA.js +7 -1
  46. package/lib/locale/ca-ES.js +7 -1
  47. package/lib/locale/de-DE.js +7 -1
  48. package/lib/locale/en-US.js +7 -1
  49. package/lib/locale/es-ES.js +7 -1
  50. package/lib/locale/fa-IR.js +7 -1
  51. package/lib/locale/fr-FR.js +7 -1
  52. package/lib/locale/id-ID.js +7 -1
  53. package/lib/locale/it-IT.js +7 -1
  54. package/lib/locale/ja-JP.js +7 -1
  55. package/lib/locale/ko-KR.js +7 -1
  56. package/lib/locale/pl-PL.js +7 -1
  57. package/lib/locale/pt-BR.js +7 -1
  58. package/lib/locale/ru-RU.js +7 -1
  59. package/lib/locale/sk-SK.js +7 -1
  60. package/lib/locale/vi-VN.js +7 -1
  61. package/lib/locale/zh-CN.js +7 -1
  62. package/lib/locale/zh-HK.js +7 -1
  63. package/lib/locale/zh-TW.js +7 -1
  64. package/lib/types/commands/operations/find-replace.operation.d.ts +1 -0
  65. package/lib/types/const.d.ts +17 -0
  66. package/lib/types/controllers/find-replace.controller.d.ts +1 -0
  67. package/lib/types/controllers/mobile/components.controller.d.ts +20 -0
  68. package/lib/types/controllers/mobile/find-replace.controller.d.ts +21 -0
  69. package/lib/types/index.d.ts +2 -1
  70. package/lib/types/locale/en-US.d.ts +7 -1
  71. package/lib/types/menu/mobile-schema.d.ts +17 -0
  72. package/lib/types/mobile-plugin.d.ts +28 -0
  73. package/lib/types/services/find-replace.service.d.ts +2 -0
  74. package/lib/types/views/mobile/MobileFindReplaceBar.d.ts +16 -0
  75. package/lib/types/views/mobile/MobileFindReplaceSettings.d.ts +16 -0
  76. package/lib/umd/index.js +1 -1
  77. package/lib/umd/locale/ar-SA.js +1 -1
  78. package/lib/umd/locale/ca-ES.js +1 -1
  79. package/lib/umd/locale/de-DE.js +1 -1
  80. package/lib/umd/locale/en-US.js +1 -1
  81. package/lib/umd/locale/es-ES.js +1 -1
  82. package/lib/umd/locale/fa-IR.js +1 -1
  83. package/lib/umd/locale/fr-FR.js +1 -1
  84. package/lib/umd/locale/id-ID.js +1 -1
  85. package/lib/umd/locale/it-IT.js +1 -1
  86. package/lib/umd/locale/ja-JP.js +1 -1
  87. package/lib/umd/locale/ko-KR.js +1 -1
  88. package/lib/umd/locale/pl-PL.js +1 -1
  89. package/lib/umd/locale/pt-BR.js +1 -1
  90. package/lib/umd/locale/ru-RU.js +1 -1
  91. package/lib/umd/locale/sk-SK.js +1 -1
  92. package/lib/umd/locale/vi-VN.js +1 -1
  93. package/lib/umd/locale/zh-CN.js +1 -1
  94. package/lib/umd/locale/zh-HK.js +1 -1
  95. package/lib/umd/locale/zh-TW.js +1 -1
  96. package/package.json +9 -9
package/lib/cjs/index.js CHANGED
@@ -5,8 +5,8 @@ let _univerjs_ui = require("@univerjs/ui");
5
5
  let _univerjs_engine_render = require("@univerjs/engine-render");
6
6
  let rxjs = require("rxjs");
7
7
  let _univerjs_icons = require("@univerjs/icons");
8
- let react = require("react");
9
8
  let react_jsx_runtime = require("react/jsx-runtime");
9
+ let react = require("react");
10
10
 
11
11
  //#region src/services/context-keys.ts
12
12
  /**
@@ -650,6 +650,13 @@ let FindReplaceService = class FindReplaceService extends _univerjs_core.Disposa
650
650
  });
651
651
  this._toggleRevealReplace(true);
652
652
  }
653
+ hideReplace() {
654
+ this._state.changeState({
655
+ replaceRevealed: false,
656
+ findString: this._state.inputtingFindString
657
+ });
658
+ this._toggleRevealReplace(false);
659
+ }
653
660
  focusSelection() {
654
661
  var _this$_model2;
655
662
  (_this$_model2 = this._model) === null || _this$_model2 === void 0 || _this$_model2.focusSelection();
@@ -775,6 +782,14 @@ const OpenReplaceDialogOperation = {
775
782
  return true;
776
783
  }
777
784
  };
785
+ const CloseFindDialogOperation = {
786
+ id: "ui.operation.close-find-dialog",
787
+ type: _univerjs_core.CommandType.OPERATION,
788
+ handler: (accessor) => {
789
+ accessor.get(IFindReplaceService).terminate();
790
+ return true;
791
+ }
792
+ };
778
793
  const GoToNextMatchOperation = {
779
794
  type: _univerjs_core.CommandType.OPERATION,
780
795
  id: "ui.operation.go-to-next-match",
@@ -810,7 +825,11 @@ function FindReplaceMenuItemFactory(accessor) {
810
825
  tooltip: "find-replace.toolbar",
811
826
  type: _univerjs_ui.MenuItemType.BUTTON,
812
827
  hidden$: (0, _univerjs_ui.getMenuHiddenObservable)(accessor, _univerjs_core.UniverInstanceType.UNIVER_SHEET),
813
- disabled$: (0, rxjs.combineLatest)([contextService.subscribeContextValue$(_univerjs_core.EDITOR_ACTIVATED), contextService.subscribeContextValue$(_univerjs_core.FOCUSING_SHEET)]).pipe((0, rxjs.map)(([editorActivated, focusingSheet]) => editorActivated || !focusingSheet))
828
+ disabled$: (0, rxjs.combineLatest)([
829
+ contextService.subscribeContextValue$(_univerjs_core.EDITOR_ACTIVATED),
830
+ contextService.subscribeContextValue$(_univerjs_core.FOCUSING_SHEET),
831
+ contextService.subscribeContextValue$(FIND_REPLACE_AVAILABLE).pipe((0, rxjs.startWith)(contextService.getContextValue(FIND_REPLACE_AVAILABLE)))
832
+ ]).pipe((0, rxjs.map)(([editorActivated, focusingSheet, available]) => editorActivated || !focusingSheet || !available))
814
833
  };
815
834
  }
816
835
 
@@ -939,6 +958,7 @@ let FindReplaceController = class FindReplaceController extends _univerjs_core.R
939
958
  [
940
959
  OpenFindDialogOperation,
941
960
  OpenReplaceDialogOperation,
961
+ CloseFindDialogOperation,
942
962
  GoToNextMatchOperation,
943
963
  GoToPreviousMatchOperation,
944
964
  ReplaceAllMatchesCommand,
@@ -962,6 +982,7 @@ let FindReplaceController = class FindReplaceController extends _univerjs_core.R
962
982
  this._menuManagerService.mergeMenu(menuSchema);
963
983
  this._findReplaceService.stateUpdates$.pipe((0, rxjs.takeUntil)(this.dispose$)).subscribe((newState) => {
964
984
  if (newState.revealed === true) this._openPanel();
985
+ else if (newState.revealed === false) this._closePanel(false);
965
986
  });
966
987
  }
967
988
  _openPanel() {
@@ -984,11 +1005,14 @@ let FindReplaceController = class FindReplaceController extends _univerjs_core.R
984
1005
  }));
985
1006
  }
986
1007
  closePanel() {
1008
+ this._closePanel(true);
1009
+ }
1010
+ _closePanel(terminateSession) {
987
1011
  if (!this._closingListenerDisposable) return;
988
1012
  this._closingListenerDisposable.dispose();
989
1013
  this._closingListenerDisposable = null;
990
1014
  this._dialogService.close(FIND_REPLACE_DIALOG_ID);
991
- this._findReplaceService.terminate();
1015
+ if (terminateSession) this._findReplaceService.terminate();
992
1016
  queueMicrotask(() => this._layoutService.focus());
993
1017
  }
994
1018
  };
@@ -1013,7 +1037,7 @@ function getFindReplaceDialogDefaultPosition(direction) {
1013
1037
  //#endregion
1014
1038
  //#region package.json
1015
1039
  var name = "@univerjs/find-replace";
1016
- var version = "1.0.0-insiders.20260809-70eefdd";
1040
+ var version = "1.0.0-rc.0";
1017
1041
 
1018
1042
  //#endregion
1019
1043
  //#region src/config/config.ts
@@ -1021,6 +1045,476 @@ const FIND_REPLACE_PLUGIN_CONFIG_KEY = "find-replace.config";
1021
1045
  const configSymbol = Symbol(FIND_REPLACE_PLUGIN_CONFIG_KEY);
1022
1046
  const defaultPluginConfig = {};
1023
1047
 
1048
+ //#endregion
1049
+ //#region src/const.ts
1050
+ /**
1051
+ * Copyright 2023-present DreamNum Co., Ltd.
1052
+ *
1053
+ * Licensed under the Apache License, Version 2.0 (the "License");
1054
+ * you may not use this file except in compliance with the License.
1055
+ * You may obtain a copy of the License at
1056
+ *
1057
+ * http://www.apache.org/licenses/LICENSE-2.0
1058
+ *
1059
+ * Unless required by applicable law or agreed to in writing, software
1060
+ * distributed under the License is distributed on an "AS IS" BASIS,
1061
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1062
+ * See the License for the specific language governing permissions and
1063
+ * limitations under the License.
1064
+ */
1065
+ const MOBILE_FIND_REPLACE_SETTINGS_COMPONENT = "MobileFindReplaceSettings";
1066
+ const MOBILE_FIND_REPLACE_SETTINGS_DIALOG_ID = "MOBILE_FIND_REPLACE_SETTINGS_DIALOG";
1067
+
1068
+ //#endregion
1069
+ //#region src/views/mobile/MobileFindReplaceSettings.tsx
1070
+ const FIND_SCOPE_OPTIONS$1 = [{
1071
+ label: "find-replace.dialog.find-scope.current-sheet",
1072
+ value: "subunit"
1073
+ }, {
1074
+ label: "find-replace.dialog.find-scope.workbook",
1075
+ value: "unit"
1076
+ }];
1077
+ const FIND_DIRECTION_OPTIONS$1 = [{
1078
+ label: "find-replace.dialog.find-direction.row",
1079
+ value: "row"
1080
+ }, {
1081
+ label: "find-replace.dialog.find-direction.column",
1082
+ value: "column"
1083
+ }];
1084
+ const FIND_BY_OPTIONS$1 = [{
1085
+ label: "find-replace.dialog.find-by.value",
1086
+ value: "value"
1087
+ }, {
1088
+ label: "find-replace.dialog.find-by.formula",
1089
+ value: "formula"
1090
+ }];
1091
+ function MobileFindReplaceSettings() {
1092
+ const findReplaceService = (0, _univerjs_ui.useDependency)(IFindReplaceService);
1093
+ const localeService = (0, _univerjs_ui.useDependency)(_univerjs_core.LocaleService);
1094
+ const state = (0, _univerjs_ui.useObservable)(findReplaceService.state$, void 0, true);
1095
+ const capabilities = (0, _univerjs_ui.useObservable)(findReplaceService.providerCapabilities$, null, true);
1096
+ function refreshSearch(force = false) {
1097
+ if (state.findString && (force || state.replaceRevealed)) findReplaceService.find();
1098
+ }
1099
+ const findScopeOptions = FIND_SCOPE_OPTIONS$1.map((option) => ({
1100
+ ...option,
1101
+ label: localeService.t(option.label)
1102
+ }));
1103
+ const findDirectionOptions = FIND_DIRECTION_OPTIONS$1.map((option) => ({
1104
+ ...option,
1105
+ label: localeService.t(option.label)
1106
+ }));
1107
+ const findByOptions = FIND_BY_OPTIONS$1.map((option) => ({
1108
+ ...option,
1109
+ label: localeService.t(option.label)
1110
+ }));
1111
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
1112
+ className: "univer-grid univer-gap-2",
1113
+ "data-u-comp": "mobile-find-replace-settings",
1114
+ children: [
1115
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingCheckbox, {
1116
+ checked: state.replaceRevealed,
1117
+ label: localeService.t("find-replace.dialog.replace"),
1118
+ onChange: (checked) => {
1119
+ if (checked) findReplaceService.revealReplace();
1120
+ else findReplaceService.hideReplace();
1121
+ refreshSearch(true);
1122
+ }
1123
+ }),
1124
+ (capabilities === null || capabilities === void 0 ? void 0 : capabilities.findDirection) && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingSelect, {
1125
+ label: localeService.t("find-replace.dialog.find-direction.title"),
1126
+ value: state.findDirection,
1127
+ options: findDirectionOptions,
1128
+ onChange: (value) => {
1129
+ findReplaceService.changeFindDirection(value);
1130
+ refreshSearch();
1131
+ }
1132
+ }),
1133
+ (capabilities === null || capabilities === void 0 ? void 0 : capabilities.findScope) && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingSelect, {
1134
+ label: localeService.t("find-replace.dialog.find-scope.title"),
1135
+ value: state.findScope,
1136
+ options: findScopeOptions,
1137
+ onChange: (value) => {
1138
+ findReplaceService.changeFindScope(value);
1139
+ refreshSearch();
1140
+ }
1141
+ }),
1142
+ (capabilities === null || capabilities === void 0 ? void 0 : capabilities.findBy) && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingSelect, {
1143
+ label: localeService.t("find-replace.dialog.find-by.title"),
1144
+ value: state.findBy,
1145
+ options: findByOptions,
1146
+ onChange: (value) => {
1147
+ findReplaceService.changeFindBy(value);
1148
+ refreshSearch();
1149
+ }
1150
+ }),
1151
+ (capabilities === null || capabilities === void 0 ? void 0 : capabilities.caseSensitive) && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingCheckbox, {
1152
+ checked: state.caseSensitive,
1153
+ label: localeService.t("find-replace.dialog.case-sensitive"),
1154
+ onChange: (checked) => {
1155
+ findReplaceService.changeCaseSensitive(checked);
1156
+ refreshSearch();
1157
+ }
1158
+ }),
1159
+ (capabilities === null || capabilities === void 0 ? void 0 : capabilities.matchesTheWholeCell) && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingCheckbox, {
1160
+ checked: state.matchesTheWholeCell,
1161
+ label: localeService.t("find-replace.dialog.match-the-whole-cell"),
1162
+ onChange: (checked) => {
1163
+ findReplaceService.changeMatchesTheWholeCell(checked);
1164
+ refreshSearch();
1165
+ }
1166
+ }),
1167
+ (capabilities === null || capabilities === void 0 ? void 0 : capabilities.matchesTheWholeWord) && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SettingCheckbox, {
1168
+ checked: state.matchesTheWholeWord,
1169
+ label: localeService.t("find-replace.dialog.match-the-whole-word"),
1170
+ onChange: (checked) => {
1171
+ findReplaceService.changeMatchesTheWholeWord(checked);
1172
+ refreshSearch();
1173
+ }
1174
+ })
1175
+ ]
1176
+ });
1177
+ }
1178
+ function SettingSelect(props) {
1179
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("label", {
1180
+ className: "univer-grid univer-gap-1 univer-text-sm univer-text-gray-700 dark:!univer-text-gray-300",
1181
+ children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", { children: props.label }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_design.MobileSelect, {
1182
+ value: props.value,
1183
+ options: props.options,
1184
+ onChange: props.onChange
1185
+ })]
1186
+ });
1187
+ }
1188
+ function SettingCheckbox(props) {
1189
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
1190
+ className: "univer-flex univer-min-h-9 univer-items-center",
1191
+ children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_design.Checkbox, {
1192
+ checked: props.checked,
1193
+ onChange: (checked) => props.onChange(Boolean(checked)),
1194
+ children: props.label
1195
+ })
1196
+ });
1197
+ }
1198
+
1199
+ //#endregion
1200
+ //#region src/controllers/mobile/components.controller.ts
1201
+ /**
1202
+ * Copyright 2023-present DreamNum Co., Ltd.
1203
+ *
1204
+ * Licensed under the Apache License, Version 2.0 (the "License");
1205
+ * you may not use this file except in compliance with the License.
1206
+ * You may obtain a copy of the License at
1207
+ *
1208
+ * http://www.apache.org/licenses/LICENSE-2.0
1209
+ *
1210
+ * Unless required by applicable law or agreed to in writing, software
1211
+ * distributed under the License is distributed on an "AS IS" BASIS,
1212
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1213
+ * See the License for the specific language governing permissions and
1214
+ * limitations under the License.
1215
+ */
1216
+ let MobileComponentsController = class MobileComponentsController extends _univerjs_core.Disposable {
1217
+ constructor(componentManager, iconManager) {
1218
+ super();
1219
+ this.disposeWithMe(iconManager.register({ SearchIcon: _univerjs_icons.SearchIcon }));
1220
+ this.disposeWithMe(componentManager.register(MOBILE_FIND_REPLACE_SETTINGS_COMPONENT, MobileFindReplaceSettings));
1221
+ }
1222
+ };
1223
+ MobileComponentsController = __decorate([__decorateParam(0, (0, _univerjs_core.Inject)(_univerjs_ui.ComponentManager)), __decorateParam(1, (0, _univerjs_core.Inject)(_univerjs_ui.IconManager))], MobileComponentsController);
1224
+
1225
+ //#endregion
1226
+ //#region src/menu/mobile-schema.ts
1227
+ const mobileMenuSchema = { [_univerjs_ui.RibbonDataGroup.ORGANIZATION]: { [OpenFindDialogOperation.id]: {
1228
+ order: 2,
1229
+ menuItemFactory: FindReplaceMenuItemFactory
1230
+ } } };
1231
+
1232
+ //#endregion
1233
+ //#region src/views/mobile/MobileFindReplaceBar.tsx
1234
+ const SEARCH_DEBOUNCE_TIME = 500;
1235
+ function MobileFindReplaceBar() {
1236
+ const findReplaceService = (0, _univerjs_ui.useDependency)(IFindReplaceService);
1237
+ (0, _univerjs_ui.useObservable)(findReplaceService.state$, void 0, true);
1238
+ if (!findReplaceService.revealed) return null;
1239
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsx)(MobileFindReplaceBarContent, {});
1240
+ }
1241
+ function MobileFindReplaceBarContent() {
1242
+ const keyboardInset = (0, react.useContext)(_univerjs_ui.MobileKeyboardInsetContext);
1243
+ const commandService = (0, _univerjs_ui.useDependency)(_univerjs_core.ICommandService);
1244
+ const dialogService = (0, _univerjs_ui.useDependency)(_univerjs_ui.IDialogService);
1245
+ const findReplaceService = (0, _univerjs_ui.useDependency)(IFindReplaceService);
1246
+ const localeService = (0, _univerjs_ui.useDependency)(_univerjs_core.LocaleService);
1247
+ const state = (0, _univerjs_ui.useObservable)(findReplaceService.state$, void 0, true);
1248
+ const currentMatch = (0, _univerjs_ui.useObservable)(findReplaceService.currentMatch$, null, true);
1249
+ const replaceables = (0, _univerjs_ui.useObservable)(findReplaceService.replaceables$, [], true);
1250
+ const [findValue, setFindValue] = (0, react.useState)(() => state.replaceRevealed ? state.inputtingFindString : state.findString);
1251
+ const inputRef = (0, react.useRef)(null);
1252
+ const searchTimerRef = (0, react.useRef)(null);
1253
+ const suppressNextFocusRef = (0, react.useRef)(false);
1254
+ (0, react.useEffect)(() => {
1255
+ const frame = requestAnimationFrame(() => {
1256
+ var _inputRef$current;
1257
+ return (_inputRef$current = inputRef.current) === null || _inputRef$current === void 0 ? void 0 : _inputRef$current.focus();
1258
+ });
1259
+ return () => cancelAnimationFrame(frame);
1260
+ }, []);
1261
+ (0, react.useEffect)(() => {
1262
+ const subscription = findReplaceService.focusSignal$.subscribe(() => {
1263
+ var _inputRef$current2;
1264
+ if (suppressNextFocusRef.current) {
1265
+ suppressNextFocusRef.current = false;
1266
+ return;
1267
+ }
1268
+ (_inputRef$current2 = inputRef.current) === null || _inputRef$current2 === void 0 || _inputRef$current2.focus();
1269
+ });
1270
+ return () => subscription.unsubscribe();
1271
+ }, [findReplaceService]);
1272
+ (0, react.useEffect)(() => () => {
1273
+ if (searchTimerRef.current) clearTimeout(searchTimerRef.current);
1274
+ }, []);
1275
+ function clearSearchTimer() {
1276
+ if (searchTimerRef.current) {
1277
+ clearTimeout(searchTimerRef.current);
1278
+ searchTimerRef.current = null;
1279
+ }
1280
+ }
1281
+ function commitSearch(value) {
1282
+ clearSearchTimer();
1283
+ if (!value) {
1284
+ findReplaceService.changeInputtingFindString("");
1285
+ return;
1286
+ }
1287
+ if (findReplaceService.replaceRevealed) {
1288
+ findReplaceService.changeInputtingFindString(value);
1289
+ findReplaceService.changeFindString(value);
1290
+ findReplaceService.find();
1291
+ return;
1292
+ }
1293
+ findReplaceService.changeFindString(value);
1294
+ }
1295
+ function scheduleSearch(value) {
1296
+ clearSearchTimer();
1297
+ if (!value) {
1298
+ commitSearch(value);
1299
+ return;
1300
+ }
1301
+ searchTimerRef.current = setTimeout(() => commitSearch(value), SEARCH_DEBOUNCE_TIME);
1302
+ }
1303
+ function blurActiveElement() {
1304
+ if (document.activeElement instanceof HTMLElement) document.activeElement.blur();
1305
+ }
1306
+ function executeAfterBlur(commandId, suppressFocusSignal = false) {
1307
+ blurActiveElement();
1308
+ if (findValue !== state.findString) {
1309
+ commitSearch(findValue);
1310
+ if (commandId === GoToNextMatchOperation.id || commandId === GoToPreviousMatchOperation.id) return;
1311
+ }
1312
+ suppressNextFocusRef.current = suppressFocusSignal;
1313
+ const execution = commandService.executeCommand(commandId);
1314
+ suppressNextFocusRef.current = false;
1315
+ execution.catch(() => void 0);
1316
+ }
1317
+ function openSettings() {
1318
+ commitSearch(findValue);
1319
+ blurActiveElement();
1320
+ dialogService.open({
1321
+ id: MOBILE_FIND_REPLACE_SETTINGS_DIALOG_ID,
1322
+ title: { title: localeService.t("find-replace.mobile.settings-title") },
1323
+ children: { label: MOBILE_FIND_REPLACE_SETTINGS_COMPONENT }
1324
+ });
1325
+ }
1326
+ const resultText = state.findCompleted && state.matchesCount === 0 ? localeService.t("find-replace.dialog.no-result") : state.matchesCount > 0 ? `${state.matchesPosition}/${state.matchesCount}` : void 0;
1327
+ const navigationDisabled = state.matchesCount === 0;
1328
+ const replaceDisabled = state.matchesCount === 0 || !(currentMatch === null || currentMatch === void 0 ? void 0 : currentMatch.replaceable);
1329
+ const replaceAllDisabled = replaceables.length === 0;
1330
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
1331
+ "data-u-comp": "mobile-find-replace-bar",
1332
+ className: "univer-fixed univer-inset-x-0 univer-z-40 univer-grid univer-gap-2 univer-bg-gray-0 univer-px-2 univer-pt-1.5 univer-shadow-[0_-4px_16px_rgba(0,0,0,0.08)] dark:!univer-bg-gray-800",
1333
+ style: {
1334
+ bottom: keyboardInset,
1335
+ paddingBottom: "calc(6px + env(safe-area-inset-bottom, 0px))"
1336
+ },
1337
+ children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
1338
+ className: "univer-flex",
1339
+ children: [
1340
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
1341
+ label: localeService.t("find-replace.mobile.settings"),
1342
+ onClick: openSettings,
1343
+ children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_icons.ConfigureTabIcon, {})
1344
+ }),
1345
+ /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
1346
+ className: "univer-relative univer-mr-2 univer-min-w-0 univer-flex-1",
1347
+ children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_icons.SearchIcon, { className: "univer-pointer-events-none univer-absolute univer-left-3 univer-top-1/2 univer-z-10 univer-size-5 -univer-translate-y-1/2 univer-text-gray-500" }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_design.Input, {
1348
+ ref: inputRef,
1349
+ size: "middle",
1350
+ allowClear: true,
1351
+ value: findValue,
1352
+ placeholder: localeService.t("find-replace.dialog.find-placeholder"),
1353
+ inputClass: "!univer-pl-10",
1354
+ slot: resultText ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
1355
+ className: "univer-text-xs univer-text-gray-400",
1356
+ children: resultText
1357
+ }) : void 0,
1358
+ onChange: (value) => {
1359
+ setFindValue(value);
1360
+ scheduleSearch(value);
1361
+ },
1362
+ onKeyDown: (event) => {
1363
+ if (event.key === "Enter") executeAfterBlur(GoToNextMatchOperation.id);
1364
+ }
1365
+ })]
1366
+ }),
1367
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
1368
+ disabled: navigationDisabled,
1369
+ label: localeService.t("find-replace.mobile.previous-match"),
1370
+ onClick: () => executeAfterBlur(GoToPreviousMatchOperation.id, true),
1371
+ children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_icons.ArrowUpIcon, {})
1372
+ }),
1373
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
1374
+ disabled: navigationDisabled,
1375
+ label: localeService.t("find-replace.mobile.next-match"),
1376
+ onClick: () => executeAfterBlur(GoToNextMatchOperation.id, true),
1377
+ children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_icons.ArrowDownIcon, {})
1378
+ }),
1379
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
1380
+ label: localeService.t("find-replace.mobile.close"),
1381
+ onClick: () => {
1382
+ blurActiveElement();
1383
+ commandService.executeCommand(CloseFindDialogOperation.id).catch(() => void 0);
1384
+ },
1385
+ children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_icons.CloseIcon, {})
1386
+ })
1387
+ ]
1388
+ }), state.replaceRevealed && /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
1389
+ className: "univer-flex univer-gap-1 univer-pl-9",
1390
+ children: [
1391
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_univerjs_design.Input, {
1392
+ size: "middle",
1393
+ className: "univer-min-w-0 univer-flex-1",
1394
+ value: state.replaceString,
1395
+ placeholder: localeService.t("find-replace.dialog.replace-placeholder"),
1396
+ onChange: (value) => findReplaceService.changeReplaceString(value)
1397
+ }),
1398
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(ActionButton, {
1399
+ disabled: replaceDisabled,
1400
+ onClick: () => executeAfterBlur(ReplaceCurrentMatchCommand.id),
1401
+ children: localeService.t("find-replace.dialog.replace")
1402
+ }),
1403
+ /* @__PURE__ */ (0, react_jsx_runtime.jsx)(ActionButton, {
1404
+ disabled: replaceAllDisabled,
1405
+ onClick: () => executeAfterBlur(ReplaceAllMatchesCommand.id),
1406
+ children: localeService.t("find-replace.dialog.replace-all")
1407
+ })
1408
+ ]
1409
+ })]
1410
+ });
1411
+ }
1412
+ function IconButton(props) {
1413
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
1414
+ type: "button",
1415
+ "aria-label": props.label,
1416
+ disabled: props.disabled,
1417
+ className: (0, _univerjs_design.clsx)(_univerjs_design.resetButtonClassName, "univer-flex univer-size-9 univer-flex-none univer-items-center univer-justify-center univer-rounded-full univer-text-lg univer-text-gray-700 active:univer-bg-gray-100 disabled:univer-opacity-35 dark:!univer-text-gray-200 dark:active:!univer-bg-gray-700"),
1418
+ onClick: props.onClick,
1419
+ children: props.children
1420
+ });
1421
+ }
1422
+ function ActionButton(props) {
1423
+ return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
1424
+ type: "button",
1425
+ disabled: props.disabled,
1426
+ className: (0, _univerjs_design.clsx)(_univerjs_design.resetButtonClassName, "univer-h-10 univer-flex-none univer-whitespace-nowrap univer-rounded-lg univer-bg-primary-600 univer-px-3 univer-text-sm univer-font-medium univer-text-gray-0 active:univer-bg-primary-700 disabled:univer-bg-gray-100 disabled:univer-text-gray-400 dark:disabled:!univer-bg-gray-700 dark:disabled:!univer-text-gray-500"),
1427
+ onClick: props.onClick,
1428
+ children: props.children
1429
+ });
1430
+ }
1431
+
1432
+ //#endregion
1433
+ //#region src/controllers/mobile/find-replace.controller.ts
1434
+ /**
1435
+ * Copyright 2023-present DreamNum Co., Ltd.
1436
+ *
1437
+ * Licensed under the Apache License, Version 2.0 (the "License");
1438
+ * you may not use this file except in compliance with the License.
1439
+ * You may obtain a copy of the License at
1440
+ *
1441
+ * http://www.apache.org/licenses/LICENSE-2.0
1442
+ *
1443
+ * Unless required by applicable law or agreed to in writing, software
1444
+ * distributed under the License is distributed on an "AS IS" BASIS,
1445
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1446
+ * See the License for the specific language governing permissions and
1447
+ * limitations under the License.
1448
+ */
1449
+ let FindReplaceMobileController = class FindReplaceMobileController extends _univerjs_core.RxDisposable {
1450
+ constructor(injector, commandService, dialogService, findReplaceService, menuManagerService, univerInstanceService, uiPartsService) {
1451
+ super();
1452
+ [
1453
+ OpenFindDialogOperation,
1454
+ OpenReplaceDialogOperation,
1455
+ CloseFindDialogOperation,
1456
+ GoToNextMatchOperation,
1457
+ GoToPreviousMatchOperation,
1458
+ ReplaceAllMatchesCommand,
1459
+ ReplaceCurrentMatchCommand,
1460
+ FocusSelectionOperation
1461
+ ].forEach((command) => this.disposeWithMe(commandService.registerCommand(command)));
1462
+ menuManagerService.mergeMenu(mobileMenuSchema);
1463
+ this.disposeWithMe(uiPartsService.registerComponent(_univerjs_ui.BuiltInUIPart.FOOTER, () => (0, _univerjs_ui.connectInjector)(MobileFindReplaceBar, injector)));
1464
+ findReplaceService.stateUpdates$.pipe((0, rxjs.takeUntil)(this.dispose$)).subscribe((state) => {
1465
+ if (state.revealed === false) dialogService.close(MOBILE_FIND_REPLACE_SETTINGS_DIALOG_ID);
1466
+ });
1467
+ let sessionUnitId = null;
1468
+ findReplaceService.stateUpdates$.pipe((0, rxjs.takeUntil)(this.dispose$)).subscribe((state) => {
1469
+ if (state.revealed === true) {
1470
+ var _univerInstanceServic;
1471
+ sessionUnitId = ((_univerInstanceServic = univerInstanceService.getFocusedUnit()) === null || _univerInstanceServic === void 0 ? void 0 : _univerInstanceServic.getUnitId()) ?? null;
1472
+ } else if (state.revealed === false) sessionUnitId = null;
1473
+ });
1474
+ univerInstanceService.focused$.pipe((0, rxjs.takeUntil)(this.dispose$)).subscribe((focused) => {
1475
+ if (sessionUnitId && focused !== sessionUnitId) findReplaceService.terminate();
1476
+ });
1477
+ }
1478
+ };
1479
+ FindReplaceMobileController = __decorate([
1480
+ __decorateParam(0, (0, _univerjs_core.Inject)(_univerjs_core.Injector)),
1481
+ __decorateParam(1, _univerjs_core.ICommandService),
1482
+ __decorateParam(2, _univerjs_ui.IDialogService),
1483
+ __decorateParam(3, IFindReplaceService),
1484
+ __decorateParam(4, _univerjs_ui.IMenuManagerService),
1485
+ __decorateParam(5, _univerjs_core.IUniverInstanceService),
1486
+ __decorateParam(6, _univerjs_ui.IUIPartsService)
1487
+ ], FindReplaceMobileController);
1488
+
1489
+ //#endregion
1490
+ //#region src/mobile-plugin.ts
1491
+ let UniverFindReplaceMobileUIPlugin = class UniverFindReplaceMobileUIPlugin extends _univerjs_core.Plugin {
1492
+ constructor(_config = defaultPluginConfig, _injector, _configService) {
1493
+ super();
1494
+ this._config = _config;
1495
+ this._injector = _injector;
1496
+ this._configService = _configService;
1497
+ const { ...rest } = (0, _univerjs_core.merge)({}, defaultPluginConfig, this._config);
1498
+ this._configService.setConfig(FIND_REPLACE_PLUGIN_CONFIG_KEY, rest);
1499
+ }
1500
+ onStarting() {
1501
+ this._injector.add([MobileComponentsController]);
1502
+ this._injector.get(MobileComponentsController);
1503
+ [[FindReplaceMobileController], [IFindReplaceService, { useClass: FindReplaceService }]].forEach((dependency) => this._injector.add(dependency));
1504
+ }
1505
+ onRendered() {
1506
+ this._injector.get(FindReplaceMobileController);
1507
+ }
1508
+ };
1509
+ _defineProperty(UniverFindReplaceMobileUIPlugin, "pluginName", "UNIVER_FIND_REPLACE_PLUGIN");
1510
+ _defineProperty(UniverFindReplaceMobileUIPlugin, "packageName", name);
1511
+ _defineProperty(UniverFindReplaceMobileUIPlugin, "version", version);
1512
+ UniverFindReplaceMobileUIPlugin = __decorate([
1513
+ (0, _univerjs_core.DependentOn)(_univerjs_ui.UniverMobileUIPlugin),
1514
+ __decorateParam(1, (0, _univerjs_core.Inject)(_univerjs_core.Injector)),
1515
+ __decorateParam(2, _univerjs_core.IConfigService)
1516
+ ], UniverFindReplaceMobileUIPlugin);
1517
+
1024
1518
  //#endregion
1025
1519
  //#region src/views/dialog/SearchInput.tsx
1026
1520
  function SearchInput(props) {
@@ -1082,10 +1576,18 @@ const FIND_BY_OPTIONS = [{
1082
1576
  value: "formula"
1083
1577
  }];
1084
1578
  function useFindInputFocus(findReplaceService, ref) {
1579
+ const pendingFocusFrameRef = (0, react.useRef)(null);
1085
1580
  const focus = (0, react.useCallback)(() => {
1086
1581
  var _document$querySelect;
1087
1582
  (_document$querySelect = document.querySelector(".univer-find-input input")) === null || _document$querySelect === void 0 || _document$querySelect.focus();
1088
1583
  }, []);
1584
+ const focusAfterDialogClose = (0, react.useCallback)(() => {
1585
+ focus();
1586
+ pendingFocusFrameRef.current = requestAnimationFrame(() => {
1587
+ pendingFocusFrameRef.current = null;
1588
+ focus();
1589
+ });
1590
+ }, [focus]);
1089
1591
  const selectHasFocus = (0, react.useCallback)(() => {
1090
1592
  const allInputs = document.querySelectorAll("[data-u-comp=find-replace-dialog] [data-u-comp=search-input]");
1091
1593
  return Array.from(allInputs).some((input) => input === document.activeElement);
@@ -1096,10 +1598,14 @@ function useFindInputFocus(findReplaceService, ref) {
1096
1598
  }));
1097
1599
  (0, react.useEffect)(() => {
1098
1600
  const subscription = findReplaceService.focusSignal$.subscribe(() => focus());
1099
- return () => subscription.unsubscribe();
1601
+ return () => {
1602
+ subscription.unsubscribe();
1603
+ if (pendingFocusFrameRef.current !== null) cancelAnimationFrame(pendingFocusFrameRef.current);
1604
+ };
1100
1605
  }, [findReplaceService, focus]);
1101
1606
  return {
1102
1607
  focus,
1608
+ focusAfterDialogClose,
1103
1609
  selectHasFocus
1104
1610
  };
1105
1611
  }
@@ -1145,7 +1651,7 @@ const ReplaceDialog = (0, react.forwardRef)(function ReplaceDialogImpl(_props, r
1145
1651
  const replaceAllDisabled = replaceables.length === 0;
1146
1652
  const onFindStringChange = (0, react.useCallback)((newValue) => findReplaceService.changeInputtingFindString(newValue), [findReplaceService]);
1147
1653
  const onReplaceStringChange = (0, react.useCallback)((replaceString) => findReplaceService.changeReplaceString(replaceString), [findReplaceService]);
1148
- const { focus } = useFindInputFocus(findReplaceService, ref);
1654
+ const { focusAfterDialogClose } = useFindInputFocus(findReplaceService, ref);
1149
1655
  const onClickFindButton = (0, react.useCallback)(() => {
1150
1656
  if (findString === inputtingFindString) findReplaceService.moveToNextMatch();
1151
1657
  else {
@@ -1160,8 +1666,8 @@ const ReplaceDialog = (0, react.forwardRef)(function ReplaceDialogImpl(_props, r
1160
1666
  const onClickReplaceButton = (0, react.useCallback)(() => commandService.executeCommand(ReplaceCurrentMatchCommand.id), [commandService]);
1161
1667
  const onClickReplaceAllButton = (0, react.useCallback)(async () => {
1162
1668
  await commandService.executeCommand(ReplaceAllMatchesCommand.id);
1163
- focus();
1164
- }, [commandService, focus]);
1669
+ focusAfterDialogClose();
1670
+ }, [commandService, focusAfterDialogClose]);
1165
1671
  const onChangeFindDirection = (0, react.useCallback)((findDirection) => {
1166
1672
  findReplaceService.changeFindDirection(findDirection);
1167
1673
  }, [findReplaceService]);
@@ -1385,6 +1891,7 @@ _defineProperty(UniverFindReplacePlugin, "version", version);
1385
1891
  UniverFindReplacePlugin = __decorate([__decorateParam(1, (0, _univerjs_core.Inject)(_univerjs_core.Injector)), __decorateParam(2, _univerjs_core.IConfigService)], UniverFindReplacePlugin);
1386
1892
 
1387
1893
  //#endregion
1894
+ exports.CloseFindDialogOperation = CloseFindDialogOperation;
1388
1895
  exports.FindBy = FindBy;
1389
1896
  exports.FindDirection = FindDirection;
1390
1897
  exports.FindModel = FindModel;
@@ -1416,6 +1923,12 @@ exports.OpenFindDialogOperation = OpenFindDialogOperation;
1416
1923
  exports.OpenReplaceDialogOperation = OpenReplaceDialogOperation;
1417
1924
  exports.ReplaceAllMatchesCommand = ReplaceAllMatchesCommand;
1418
1925
  exports.ReplaceCurrentMatchCommand = ReplaceCurrentMatchCommand;
1926
+ Object.defineProperty(exports, 'UniverFindReplaceMobileUIPlugin', {
1927
+ enumerable: true,
1928
+ get: function () {
1929
+ return UniverFindReplaceMobileUIPlugin;
1930
+ }
1931
+ });
1419
1932
  Object.defineProperty(exports, 'UniverFindReplacePlugin', {
1420
1933
  enumerable: true,
1421
1934
  get: function () {
@@ -2,10 +2,16 @@
2
2
  //#region src/locale/ar-SA.ts
3
3
  const locale = { "find-replace": {
4
4
  toolbar: "بحث واستبدال",
5
+ mobile: {
6
+ settings: "إعدادات البحث والاستبدال",
7
+ "settings-title": "إعدادات البحث والاستبدال",
8
+ "previous-match": "التطابق السابق",
9
+ "next-match": "التطابق التالي",
10
+ close: "إغلاق البحث والاستبدال"
11
+ },
5
12
  shortcut: {
6
13
  "open-find-dialog": "فتح مربع حوار البحث",
7
14
  "open-replace-dialog": "فتح مربع حوار الاستبدال",
8
- "close-dialog": "إغلاق مربع حوار البحث والاستبدال",
9
15
  "go-to-next-match": "الانتقال إلى التطابق التالي",
10
16
  "go-to-previous-match": "الانتقال إلى التطابق السابق",
11
17
  "focus-selection": "تركيز التحديد",
@@ -2,10 +2,16 @@
2
2
  //#region src/locale/ca-ES.ts
3
3
  const locale = { "find-replace": {
4
4
  toolbar: "Cerca i reemplaça",
5
+ mobile: {
6
+ settings: "Configuració de cerca i reemplaçament",
7
+ "settings-title": "Configuració de cerca i reemplaçament",
8
+ "previous-match": "Coincidència anterior",
9
+ "next-match": "Coincidència següent",
10
+ close: "Tanca la cerca i el reemplaçament"
11
+ },
5
12
  shortcut: {
6
13
  "open-find-dialog": "Obrir el diàleg de cerca",
7
14
  "open-replace-dialog": "Obrir el diàleg de reemplaçament",
8
- "close-dialog": "Tancar el diàleg de cerca i reemplaçament",
9
15
  "go-to-next-match": "Anar a la següent coincidència",
10
16
  "go-to-previous-match": "Anar a la coincidència anterior",
11
17
  "focus-selection": "Enfocar la selecció",