@topconsultnpm/sdkui-react 6.22.0-dev2.8 → 6.22.0-dev3.10

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 (311) hide show
  1. package/lib/components/NewComponents/ContextMenu/TMContextMenu.js +3 -3
  2. package/lib/components/NewComponents/ContextMenu/hooks.d.ts +1 -1
  3. package/lib/components/NewComponents/ContextMenu/styles.d.ts +14 -14
  4. package/lib/components/NewComponents/FloatingMenuBar/TMFloatingMenuBar.js +6 -6
  5. package/lib/components/NewComponents/FloatingMenuBar/styles.d.ts +35 -35
  6. package/lib/components/base/Styled.d.ts +5 -5
  7. package/lib/components/base/Styled.js +7 -5
  8. package/lib/components/base/TMAccordionNew.js +7 -7
  9. package/lib/components/base/TMAlert.d.ts +32 -32
  10. package/lib/components/base/TMAreaManager.js +1 -1
  11. package/lib/components/base/TMButton.js +4 -4
  12. package/lib/components/base/TMClosableList.js +3 -3
  13. package/lib/components/base/TMCounterBar.d.ts +2 -2
  14. package/lib/components/base/TMCounterContainer.d.ts +1 -2
  15. package/lib/components/base/TMCustomButton.d.ts +1 -1
  16. package/lib/components/base/TMCustomButton.js +1 -1
  17. package/lib/components/base/TMDataGrid.d.ts +4 -0
  18. package/lib/components/base/TMDataGrid.js +292 -12
  19. package/lib/components/base/TMDataGridExportForm.d.ts +1 -2
  20. package/lib/components/base/TMDropDownMenu.js +1 -1
  21. package/lib/components/base/TMEditorBase.d.ts +2 -0
  22. package/lib/components/base/TMFileManager.d.ts +1 -2
  23. package/lib/components/base/TMFileManager.js +5 -3
  24. package/lib/components/base/TMFileManagerDataGridView.d.ts +1 -2
  25. package/lib/components/base/TMFileManagerDataGridView.js +12 -3
  26. package/lib/components/base/TMFileManagerThumbnailItems.d.ts +1 -1
  27. package/lib/components/base/TMFileManagerThumbnailItems.js +20 -10
  28. package/lib/components/base/TMFileManagerThumbnailsView.d.ts +1 -1
  29. package/lib/components/base/TMFileManagerUtils.d.ts +4 -2
  30. package/lib/components/base/TMFileManagerUtils.js +37 -1
  31. package/lib/components/base/TMLayout.d.ts +6 -6
  32. package/lib/components/base/TMLayout.js +3 -3
  33. package/lib/components/base/TMList.d.ts +1 -2
  34. package/lib/components/base/TMList.js +1 -1
  35. package/lib/components/base/TMListView.d.ts +1 -1
  36. package/lib/components/base/TMListView.js +3 -3
  37. package/lib/components/base/TMModal.d.ts +11 -0
  38. package/lib/components/base/TMModal.js +47 -13
  39. package/lib/components/base/TMPanel.d.ts +6 -0
  40. package/lib/components/base/TMPanel.js +141 -28
  41. package/lib/components/base/TMPopUp.js +5 -2
  42. package/lib/components/base/TMResizableMenu.js +2 -2
  43. package/lib/components/base/TMRightSidebar.js +1 -1
  44. package/lib/components/base/TMShowAllOrMaxItemsButton.js +1 -1
  45. package/lib/components/base/TMSpinner.d.ts +1 -2
  46. package/lib/components/base/TMSpinner.js +2 -2
  47. package/lib/components/base/TMTab.d.ts +3 -4
  48. package/lib/components/base/TMTab.js +2 -2
  49. package/lib/components/base/TMTabControl.d.ts +101 -0
  50. package/lib/components/base/TMTabControl.js +653 -0
  51. package/lib/components/base/TMToggleButton.js +2 -2
  52. package/lib/components/base/TMToolbarCard.js +3 -3
  53. package/lib/components/base/TMTooltip.d.ts +2 -1
  54. package/lib/components/base/TMTooltip.js +24 -8
  55. package/lib/components/base/TMTreeView.d.ts +1 -1
  56. package/lib/components/base/TMTreeView.js +123 -70
  57. package/lib/components/base/TMUserAvatar.d.ts +1 -2
  58. package/lib/components/base/TMVilViewer.d.ts +1 -2
  59. package/lib/components/base/TMWaitPanel.d.ts +2 -3
  60. package/lib/components/base/TMWaitPanel.js +2 -2
  61. package/lib/components/choosers/TMCultureIDPicker.js +2 -2
  62. package/lib/components/choosers/TMDataListItemChooser.js +1 -1
  63. package/lib/components/choosers/TMDataListItemPicker.js +2 -2
  64. package/lib/components/choosers/TMDcmtTypeChooser.js +5 -4
  65. package/lib/components/choosers/TMDiskChooser.js +1 -1
  66. package/lib/components/choosers/TMDistinctValues.d.ts +9 -7
  67. package/lib/components/choosers/TMDistinctValues.js +157 -141
  68. package/lib/components/choosers/TMDynDataListItemChooser.d.ts +1 -1
  69. package/lib/components/choosers/TMDynDataListItemChooser.js +1 -1
  70. package/lib/components/choosers/TMImageIDChooser.js +1 -1
  71. package/lib/components/choosers/TMInvoiceRetrieveFormats.d.ts +1 -2
  72. package/lib/components/choosers/TMMetadataChooser.js +3 -3
  73. package/lib/components/choosers/TMOrderRetrieveFormats.d.ts +1 -2
  74. package/lib/components/choosers/TMQuickSearchInfo.d.ts +12 -0
  75. package/lib/components/choosers/TMQuickSearchInfo.js +279 -0
  76. package/lib/components/choosers/TMQuickSearchSettingsForm.d.ts +16 -0
  77. package/lib/components/choosers/TMQuickSearchSettingsForm.js +94 -0
  78. package/lib/components/choosers/TMRelationChooser.d.ts +3 -3
  79. package/lib/components/choosers/TMRelationChooser.js +1 -1
  80. package/lib/components/choosers/TMSelectedValuesSummary.d.ts +13 -0
  81. package/lib/components/choosers/TMSelectedValuesSummary.js +89 -0
  82. package/lib/components/choosers/TMUserChooser.d.ts +2 -2
  83. package/lib/components/choosers/TMUserChooser.js +1 -1
  84. package/lib/components/editors/TMCheckBox.js +1 -1
  85. package/lib/components/editors/TMDropDown.d.ts +3 -0
  86. package/lib/components/editors/TMDropDown.js +197 -5
  87. package/lib/components/editors/TMEditorStyled.d.ts +10 -10
  88. package/lib/components/editors/TMFormulaEditor.d.ts +1 -1
  89. package/lib/components/editors/TMFormulaEditor.js +1 -1
  90. package/lib/components/editors/TMHtmlContentDisplay.d.ts +1 -2
  91. package/lib/components/editors/TMHtmlContentDisplay.js +1 -1
  92. package/lib/components/editors/TMHtmlEditor.d.ts +1 -2
  93. package/lib/components/editors/TMLocalizedTextBox.js +1 -1
  94. package/lib/components/editors/TMMetadataEditor.d.ts +5 -1
  95. package/lib/components/editors/TMMetadataEditor.js +8 -3
  96. package/lib/components/editors/TMMetadataValues.js +6 -6
  97. package/lib/components/editors/TMRadioButton.js +2 -2
  98. package/lib/components/editors/TMSummary.js +3 -3
  99. package/lib/components/editors/TMTextArea.js +3 -3
  100. package/lib/components/editors/TMTextBox.js +3 -3
  101. package/lib/components/editors/TMTextExpression.js +1 -1
  102. package/lib/components/editors/TMTreeDropDown.d.ts +1 -1
  103. package/lib/components/features/archive/TMArchive.js +17 -3
  104. package/lib/components/features/assistant/TMToppyDraggableHelpCenter.d.ts +1 -1
  105. package/lib/components/features/assistant/TMToppyDraggableHelpCenter.js +2 -2
  106. package/lib/components/features/assistant/TMToppySpeechBubble.js +1 -1
  107. package/lib/components/features/blog/TMBlogCommentForm.d.ts +1 -2
  108. package/lib/components/features/documents/TMBatchUpdateForm.js +20 -6
  109. package/lib/components/features/documents/TMCopyToFolderForm.js +61 -22
  110. package/lib/components/features/documents/TMDcmtBlog.d.ts +3 -0
  111. package/lib/components/features/documents/TMDcmtBlog.js +4 -4
  112. package/lib/components/features/documents/TMDcmtForm.d.ts +7 -0
  113. package/lib/components/features/documents/TMDcmtForm.js +181 -54
  114. package/lib/components/features/documents/TMDcmtFormActionButtons.d.ts +12 -1
  115. package/lib/components/features/documents/TMDcmtFormActionButtons.js +79 -9
  116. package/lib/components/features/documents/TMDcmtIcon.d.ts +1 -2
  117. package/lib/components/features/documents/TMDcmtIcon.js +5 -3
  118. package/lib/components/features/documents/TMDcmtPreview.d.ts +1 -1
  119. package/lib/components/features/documents/TMDcmtPreview.js +12 -8
  120. package/lib/components/features/documents/TMDcmtTasks.d.ts +1 -2
  121. package/lib/components/features/documents/TMDownloadRelationViewerSection.js +1 -1
  122. package/lib/components/features/documents/TMDragDropOverlay.d.ts +1 -1
  123. package/lib/components/features/documents/TMFileUploader.js +3 -3
  124. package/lib/components/features/documents/TMMasterDetailDcmts.js +116 -34
  125. package/lib/components/features/documents/TMMasterInfoFields.d.ts +19 -0
  126. package/lib/components/features/documents/TMMasterInfoFields.js +184 -0
  127. package/lib/components/features/documents/TMMergeToPdfForm.d.ts +2 -4
  128. package/lib/components/features/documents/TMMergeToPdfForm.js +42 -10
  129. package/lib/components/features/documents/TMMultiMasterDetailDcmtsForm.d.ts +45 -0
  130. package/lib/components/features/documents/TMMultiMasterDetailDcmtsForm.js +321 -0
  131. package/lib/components/features/documents/TMMultiMasterDetailDcmtsUtils.d.ts +370 -0
  132. package/lib/components/features/documents/TMMultiMasterDetailDcmtsUtils.js +283 -0
  133. package/lib/components/features/documents/TMRelationViewer.d.ts +24 -3
  134. package/lib/components/features/documents/TMRelationViewer.js +110 -52
  135. package/lib/components/features/documents/copyAndMergeDcmtsShared.d.ts +1 -1
  136. package/lib/components/features/search/TMDcmtCheckoutInfoForm.d.ts +1 -2
  137. package/lib/components/features/search/TMMetadataOutputForm.d.ts +1 -2
  138. package/lib/components/features/search/TMMetadataOutputForm.js +1 -1
  139. package/lib/components/features/search/TMMetadataSorterForm.d.ts +1 -2
  140. package/lib/components/features/search/TMMetadataSorterForm.js +1 -1
  141. package/lib/components/features/search/TMSavedQuerySelector.d.ts +2 -2
  142. package/lib/components/features/search/TMSavedQuerySelector.js +2 -2
  143. package/lib/components/features/search/TMSearch.d.ts +1 -2
  144. package/lib/components/features/search/TMSearch.js +146 -21
  145. package/lib/components/features/search/TMSearchQueryEditor.js +7 -5
  146. package/lib/components/features/search/TMSearchQueryPanel.d.ts +4 -0
  147. package/lib/components/features/search/TMSearchQueryPanel.js +142 -68
  148. package/lib/components/features/search/TMSearchResult.d.ts +16 -0
  149. package/lib/components/features/search/TMSearchResult.js +439 -110
  150. package/lib/components/features/search/TMSearchResultFloatingActionButton.d.ts +1 -1
  151. package/lib/components/features/search/TMSignatureInfoContent.d.ts +1 -2
  152. package/lib/components/features/search/TMSignatureInfoContent.js +1 -1
  153. package/lib/components/features/search/TMTreeSelector.js +121 -70
  154. package/lib/components/features/search/TMViewHistoryDcmt.d.ts +1 -2
  155. package/lib/components/features/tasks/TMTaskForm.d.ts +1 -1
  156. package/lib/components/features/tasks/TMTaskForm.js +1 -1
  157. package/lib/components/features/tasks/TMTaskFormUtils.d.ts +10 -10
  158. package/lib/components/features/tasks/TMTaskFormUtils.js +3 -3
  159. package/lib/components/features/tasks/TMTasksAgenda.d.ts +1 -1
  160. package/lib/components/features/tasks/TMTasksAgenda.js +1 -1
  161. package/lib/components/features/tasks/TMTasksCalendar.d.ts +1 -1
  162. package/lib/components/features/tasks/TMTasksCalendar.js +1 -1
  163. package/lib/components/features/tasks/TMTasksHeader.d.ts +1 -1
  164. package/lib/components/features/tasks/TMTasksHeader.js +1 -1
  165. package/lib/components/features/tasks/TMTasksPanelContent.d.ts +1 -1
  166. package/lib/components/features/tasks/TMTasksUtilsView.d.ts +5 -5
  167. package/lib/components/features/tasks/TMTasksUtilsView.js +1 -1
  168. package/lib/components/features/tasks/TMTasksView.d.ts +1 -1
  169. package/lib/components/features/tasks/TMTasksView.js +7 -13
  170. package/lib/components/features/wg/TMWGsCopyMoveForm.d.ts +2 -3
  171. package/lib/components/features/wg/TMWGsCopyMoveForm.js +1 -1
  172. package/lib/components/features/workflow/TMWorkflowPopup.d.ts +17 -8
  173. package/lib/components/features/workflow/TMWorkflowPopup.js +9 -5
  174. package/lib/components/features/workflow/diagram/ConnectionComponent.js +3 -3
  175. package/lib/components/features/workflow/diagram/DiagramItemComponent.js +3 -3
  176. package/lib/components/features/workflow/diagram/DiagramItemForm.js +1 -1
  177. package/lib/components/features/workflow/diagram/DiagramItemSvgContent.js +1 -1
  178. package/lib/components/features/workflow/diagram/RecipientList.js +1 -1
  179. package/lib/components/features/workflow/diagram/WFDiagram.js +4 -4
  180. package/lib/components/forms/Login/Chooser.d.ts +2 -2
  181. package/lib/components/forms/Login/Menu.js +1 -1
  182. package/lib/components/forms/Login/OTPReader.js +1 -1
  183. package/lib/components/forms/Login/PasswordStrengthChecker.js +1 -1
  184. package/lib/components/forms/Login/RapidAccessLogin.js +2 -2
  185. package/lib/components/forms/Login/RecoverPasswordFlow.js +2 -2
  186. package/lib/components/forms/Login/SelectBox.js +1 -1
  187. package/lib/components/forms/Login/StepIndicator.js +1 -1
  188. package/lib/components/forms/Login/TMLoginForm.js +7 -7
  189. package/lib/components/forms/Login/TextBox.js +1 -1
  190. package/lib/components/forms/TMApplyForm.js +3 -3
  191. package/lib/components/forms/TMChooserForm.d.ts +1 -2
  192. package/lib/components/forms/TMChooserForm.js +1 -1
  193. package/lib/components/forms/TMSaveForm.d.ts +4 -4
  194. package/lib/components/forms/TMSaveForm.js +3 -3
  195. package/lib/components/grids/TMBlogAttachments.d.ts +1 -2
  196. package/lib/components/grids/TMBlogAttachments.js +14 -3
  197. package/lib/components/grids/TMBlogHeader.d.ts +1 -1
  198. package/lib/components/grids/TMBlogHeader.js +5 -1
  199. package/lib/components/grids/TMBlogsPost.d.ts +3 -1
  200. package/lib/components/grids/TMBlogsPost.js +31 -4
  201. package/lib/components/grids/TMBlogsPostUtils.d.ts +10 -9
  202. package/lib/components/grids/TMBlogsPostUtils.js +15 -4
  203. package/lib/components/grids/TMRecentsManager.js +4 -4
  204. package/lib/components/grids/TMValidationItemsList.d.ts +1 -2
  205. package/lib/components/grids/TMValidationItemsList.js +1 -1
  206. package/lib/components/index.d.ts +2 -0
  207. package/lib/components/index.js +2 -0
  208. package/lib/components/layout/panelManager/TMPanelManagerContainer.d.ts +2 -2
  209. package/lib/components/layout/panelManager/TMPanelManagerContainer.js +25 -15
  210. package/lib/components/layout/panelManager/TMPanelManagerContext.d.ts +2 -2
  211. package/lib/components/layout/panelManager/TMPanelManagerContext.js +68 -93
  212. package/lib/components/layout/panelManager/TMPanelManagerToolbar.d.ts +3 -3
  213. package/lib/components/layout/panelManager/TMPanelManagerToolbar.js +1 -1
  214. package/lib/components/layout/panelManager/TMPanelManagerWithPersistenceProvider.d.ts +2 -2
  215. package/lib/components/layout/panelManager/TMPanelWrapper.d.ts +2 -2
  216. package/lib/components/layout/panelManager/TMPanelWrapper.js +3 -3
  217. package/lib/components/layout/panelManager/types.d.ts +3 -0
  218. package/lib/components/layout/panelManager/utils.js +13 -11
  219. package/lib/components/pages/TMPage.d.ts +1 -1
  220. package/lib/components/pages/TMPage.js +1 -1
  221. package/lib/components/query/TMQueryCountButton.js +1 -1
  222. package/lib/components/query/TMQueryEditor.js +7 -7
  223. package/lib/components/settings/SettingsAppearance.d.ts +1 -2
  224. package/lib/components/sidebar/TMAboutApp.d.ts +1 -2
  225. package/lib/components/sidebar/TMCommandsPanel.js +1 -1
  226. package/lib/components/sidebar/TMHeader.d.ts +3 -3
  227. package/lib/components/sidebar/TMHeader.js +36 -26
  228. package/lib/components/sidebar/TMSidebar.js +1 -1
  229. package/lib/components/sidebar/TMSidebarItem.js +1 -1
  230. package/lib/components/viewers/TMDataListItemViewer.d.ts +2 -3
  231. package/lib/components/viewers/TMDataUserIdItemViewer.d.ts +2 -3
  232. package/lib/components/viewers/TMMidViewer.d.ts +2 -2
  233. package/lib/components/viewers/TMMidViewer.js +6 -3
  234. package/lib/components/viewers/TMTidViewer.d.ts +2 -2
  235. package/lib/components/viewers/TMTidViewer.js +89 -28
  236. package/lib/components/wizard/TMStepIndicator.js +3 -3
  237. package/lib/css/tm-sdkui.css +1 -1
  238. package/lib/devextreme-license.d.ts +1 -0
  239. package/lib/devextreme-license.js +3 -0
  240. package/lib/helper/Enum_Localizator.d.ts +4 -4
  241. package/lib/helper/Globalization.d.ts +1 -1
  242. package/lib/helper/SDKUI_Globals.d.ts +110 -0
  243. package/lib/helper/SDKUI_Globals.js +151 -0
  244. package/lib/helper/SDKUI_Localizator.d.ts +735 -687
  245. package/lib/helper/SDKUI_Localizator.js +480 -0
  246. package/lib/helper/TMAppUpdatedModal.d.ts +1 -0
  247. package/lib/helper/TMAppUpdatedModal.js +134 -0
  248. package/lib/helper/TMCommandsContextMenu.d.ts +1 -1
  249. package/lib/helper/TMIcons.d.ts +280 -279
  250. package/lib/helper/TMIcons.js +4 -3
  251. package/lib/helper/TMPdfViewer.d.ts +1 -2
  252. package/lib/helper/TMPdfViewer.js +1 -1
  253. package/lib/helper/TMToppyMessage.d.ts +2 -2
  254. package/lib/helper/TMToppyMessage.js +1 -1
  255. package/lib/helper/TMUtils.d.ts +14 -1
  256. package/lib/helper/TMUtils.js +25 -3
  257. package/lib/helper/checkinCheckoutManager.d.ts +1 -1
  258. package/lib/helper/checkinCheckoutManager.js +1 -1
  259. package/lib/helper/dataGridSearchHelper.d.ts +28 -0
  260. package/lib/helper/dataGridSearchHelper.js +51 -0
  261. package/lib/helper/dcmtsHelper.d.ts +20 -0
  262. package/lib/helper/dcmtsHelper.js +58 -1
  263. package/lib/helper/helpers.d.ts +13 -2
  264. package/lib/helper/helpers.js +27 -3
  265. package/lib/helper/index.d.ts +2 -0
  266. package/lib/helper/index.js +2 -0
  267. package/lib/helper/queryHelper.d.ts +6 -1
  268. package/lib/helper/queryHelper.js +8 -3
  269. package/lib/hooks/tmDistinctValuesGridHelper.d.ts +16 -0
  270. package/lib/hooks/tmDistinctValuesGridHelper.js +31 -0
  271. package/lib/hooks/useArchiveListForm.d.ts +39 -0
  272. package/lib/hooks/useArchiveListForm.js +46 -0
  273. package/lib/hooks/useCaseFlowApprove.d.ts +56 -0
  274. package/lib/hooks/useCaseFlowApprove.js +157 -0
  275. package/lib/hooks/useDataUserIdItem.d.ts +1 -0
  276. package/lib/hooks/useDataUserIdItem.js +1 -0
  277. package/lib/hooks/useDcmtOperations.d.ts +7 -0
  278. package/lib/hooks/useDcmtOperations.js +141 -71
  279. package/lib/hooks/useDocumentOperations.d.ts +4 -0
  280. package/lib/hooks/useDocumentOperations.js +53 -11
  281. package/lib/hooks/useInputDialog.d.ts +1 -2
  282. package/lib/hooks/useInputDialog.js +1 -1
  283. package/lib/hooks/useMultiMasterDetailDcmts.d.ts +113 -0
  284. package/lib/hooks/useMultiMasterDetailDcmts.js +760 -0
  285. package/lib/hooks/useQueryParametersDialog.js +1 -1
  286. package/lib/hooks/useRelatedDocuments.d.ts +1 -0
  287. package/lib/hooks/useRelatedDocuments.js +22 -27
  288. package/lib/hooks/useShowDossiersV5.d.ts +12 -0
  289. package/lib/hooks/useShowDossiersV5.js +37 -0
  290. package/lib/hooks/useTMDistinctValuesMetadataDisplay.d.ts +18 -0
  291. package/lib/hooks/useTMDistinctValuesMetadataDisplay.js +103 -0
  292. package/lib/hooks/useTMDistinctValuesQuickSearch.d.ts +49 -0
  293. package/lib/hooks/useTMDistinctValuesQuickSearch.js +307 -0
  294. package/lib/hooks/useTMDistinctValuesSelection.d.ts +42 -0
  295. package/lib/hooks/useTMDistinctValuesSelection.js +103 -0
  296. package/lib/hooks/useTMDistinctValuesSource.d.ts +29 -0
  297. package/lib/hooks/useTMDistinctValuesSource.js +105 -0
  298. package/lib/index.d.ts +2 -0
  299. package/lib/index.js +5 -2
  300. package/lib/services/caseflow/CaseFlowService.d.ts +247 -0
  301. package/lib/services/caseflow/CaseFlowService.js +720 -0
  302. package/lib/services/caseflow/CaseFlowTemplateCacheService.d.ts +28 -0
  303. package/lib/services/caseflow/CaseFlowTemplateCacheService.js +121 -0
  304. package/lib/services/caseflow/caseFlowNameCache.d.ts +32 -0
  305. package/lib/services/caseflow/caseFlowNameCache.js +116 -0
  306. package/lib/services/caseflow/caseFlowWorkItemUtils.d.ts +61 -0
  307. package/lib/services/caseflow/caseFlowWorkItemUtils.js +113 -0
  308. package/lib/services/index.d.ts +4 -0
  309. package/lib/services/index.js +4 -0
  310. package/lib/services/platform_services.d.ts +6 -7
  311. package/package.json +16 -13
@@ -1,17 +1,17 @@
1
- import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
2
- import { useCallback, useEffect, useMemo, useState } from 'react';
1
+ import { Fragment as _Fragment, jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useCallback, useEffect, useMemo, useRef, useState } from 'react';
3
3
  import { SavedQueryCacheService, DcmtTypeListCacheService, SDK_Localizator, LayoutModes } from '@topconsultnpm/sdk-ts';
4
4
  import TMSavedQuerySelector from './TMSavedQuerySelector';
5
5
  import TMTreeSelector from './TMTreeSelector';
6
- import { TabPanel, Item } from 'devextreme-react/tab-panel';
7
6
  import TMSearchQueryPanel, { refreshLastSearch } from './TMSearchQueryPanel';
8
- import { getSysAllDcmtsSQD, IconFilter, IconRecentlyViewed, IconSavedQuery, IconTree, mergeSearchResultsAppend, removeMruTid, SDKUI_Globals, SDKUI_Localizator, updateMruTids } from '../../../helper';
7
+ import { getSysAllDcmtsSQD, SYS_ALL_DCMTS_SQD_ID, IconFilter, IconRecentlyViewed, IconSavedQuery, IconTree, mergeSearchResultsAppend, removeMruTid, SDKUI_Globals, SDKUI_Localizator, updateMruTids } from '../../../helper';
9
8
  import TMSearchResult from './TMSearchResult';
9
+ import TMTabControl, { TMTabPanel, useTMTabs } from '../../base/TMTabControl';
10
10
  import TMRecentsManager from '../../grids/TMRecentsManager';
11
11
  import { SearchResultContext } from '../../../ts';
12
12
  import { useDeviceType, DeviceType } from '../../base/TMDeviceProvider';
13
13
  import { StyledMultiViewPanel } from '../../base/Styled';
14
- import { useTMPanelManagerContext } from '../../layout/panelManager/TMPanelManagerContext';
14
+ import { TMPanelManagerProvider, useTMPanelManagerContext } from '../../layout/panelManager/TMPanelManagerContext';
15
15
  import TMPanelManagerContainer from '../../layout/panelManager/TMPanelManagerContainer';
16
16
  import { TMPanelManagerWithPersistenceProvider } from '../../layout/panelManager/TMPanelManagerWithPersistenceProvider';
17
17
  import { TMExceptionBoxManager } from '../../base/TMPopUp';
@@ -20,7 +20,7 @@ var TMSearchViews;
20
20
  TMSearchViews[TMSearchViews["Search"] = 0] = "Search";
21
21
  TMSearchViews[TMSearchViews["Result"] = 1] = "Result";
22
22
  })(TMSearchViews || (TMSearchViews = {}));
23
- const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTaskCallback, editTaskCallback, handleNavigateToWGs, handleNavigateToDossiers, openInOffice, isVisible, inputTID, inputSqdID, inputMids, isExpertMode = SDKUI_Globals.userSettings.advancedSettings.expertMode === 1, floatingActionConfig, onFileOpened, onRefreshAfterAddDcmtToFavs, onTaskCreateRequest, openWGsCopyMoveForm, editPdfForm = false, openS4TViewer, onOpenS4TViewerRequest, onOpenPdfEditorRequest, openFileUploaderPdfEditor, showTodoDcmtForm, showToppyDraggableHelpCenter = true, toppyHelpCenterUsePortal = false, passToArchiveCallback, onCurrentTIDChangedCallback, onlyShowSearchQueryPanel, onReferenceClick, refreshFavoriteSavedQueries, inputDID, formAutoOpen, fetchRemoteCertificates, graphometricManager }) => {
23
+ const TMSearchInstance = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTaskCallback, editTaskCallback, handleNavigateToWGs, handleNavigateToDossiers, openInOffice, isVisible, inputTID, inputSqdID, inputMids, isExpertMode = SDKUI_Globals.userSettings.advancedSettings.expertMode === 1, floatingActionConfig, onFileOpened, onRefreshAfterAddDcmtToFavs, onTaskCreateRequest, openWGsCopyMoveForm, editPdfForm = false, openS4TViewer, onOpenS4TViewerRequest, onOpenPdfEditorRequest, openFileUploaderPdfEditor, showTodoDcmtForm, showToppyDraggableHelpCenter = true, toppyHelpCenterUsePortal = false, passToArchiveCallback, onCurrentTIDChangedCallback, onlyShowSearchQueryPanel, onReferenceClick, refreshFavoriteSavedQueries, inputDID, formAutoOpen, fetchRemoteCertificates, graphometricManager, onSelectedNameChanged }) => {
24
24
  const [allSQDs, setAllSQDs] = useState([]);
25
25
  const [filteredByTIDSQDs, setFilteredByTIDSQDs] = useState([]);
26
26
  const [currentSQD, setCurrentSQD] = useState();
@@ -32,8 +32,22 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
32
32
  const [currentSearchView, setCurrentSearchView] = useState(TMSearchViews.Search);
33
33
  const [currentSQDMode, setCurrentSQDMode] = useState(1);
34
34
  const [lastQdSearched, setLastQdSearched] = useState();
35
- const [showSearchResults, setShowSearchResults] = useState(true);
35
+ const [showSearchResults, setShowSearchResults] = useState(!onlyShowSearchQueryPanel);
36
36
  const [maxDcmtsToBeReturned, setMaxDcmtsToBeReturned] = useState(SDKUI_Globals.userSettings.searchSettings?.maxDcmtsToBeReturned ?? 1000);
37
+ // Il titolo del tab e' il nome del tipo documento dell'ultima scelta dell'utente, sia questa fatta
38
+ // dall'albero, dalle scorciatoie o da una ricerca rapida (di cui conta il tipo documento, non il nome).
39
+ // La callback sta in un ref cosi non entra nelle dipendenze di effetti e memo.
40
+ const selectedNameRef = useRef(onSelectedNameChanged);
41
+ selectedNameRef.current = onSelectedNameChanged;
42
+ // Il nome del tipo documento scelto arriva dal descrittore, che qui e' gia' in cache
43
+ const notifySelectedTIDAsync = useCallback(async (tid) => {
44
+ if (!tid || !selectedNameRef.current)
45
+ return;
46
+ const dtd = await DcmtTypeListCacheService.GetAsync(tid);
47
+ const name = dtd?.nameLoc ?? dtd?.name;
48
+ if (name)
49
+ selectedNameRef.current(name);
50
+ }, []);
37
51
  const deviceType = useDeviceType();
38
52
  useEffect(() => {
39
53
  if (onCurrentTIDChangedCallback) {
@@ -47,6 +61,7 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
47
61
  useEffect(() => {
48
62
  if (!inputTID)
49
63
  return;
64
+ notifySelectedTIDAsync(inputTID);
50
65
  setCurrentTID(inputTID);
51
66
  setCurrentSearchView(TMSearchViews.Search);
52
67
  }, [inputTID]);
@@ -54,6 +69,7 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
54
69
  const loadSqd = async () => {
55
70
  try {
56
71
  const resultSqd = await SavedQueryCacheService.GetAsync(inputSqdID);
72
+ notifySelectedTIDAsync(resultSqd?.masterTID);
57
73
  await setSQDAsync(resultSqd);
58
74
  // Mostra la vista Search per visualizzare i filtri della SavedQuery caricata
59
75
  setCurrentSearchView(TMSearchViews.Search);
@@ -141,17 +157,54 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
141
157
  setCurrentMruTID(0);
142
158
  };
143
159
  const onSQDItemClick = useCallback(async (sqd, setSqdAsync) => {
160
+ notifySelectedTIDAsync(sqd.masterTID);
144
161
  // Forza ricaricamento completo se la query è già selezionata
145
162
  if (sqd.id === currentSQD?.id) {
146
163
  await setSqdAsync(undefined);
147
164
  }
148
165
  await setSqdAsync(sqd);
149
- }, [currentSQD]);
166
+ }, [currentSQD, notifySelectedTIDAsync]);
150
167
  const onSQDDeleted = useCallback(async (sqd, sqdToBeSet, setSqdAsync) => {
151
168
  await loadDataSQDsAsync(true, sqd.masterTID);
152
169
  if (sqdToBeSet)
153
170
  await setSqdAsync?.(sqdToBeSet);
154
171
  }, []);
172
+ // --- REFRESH DEI PANNELLI ---
173
+ // Scorciatoie: rilegge dal server l'elenco dei tipi documento, così le scorciatoie riflettono
174
+ // quelli aggiunti o rimossi. La nuova identità di mruTIDs fa ricaricare i descrittori a TMRecentsManager.
175
+ const refreshRecentsAsync = useCallback(async () => {
176
+ DcmtTypeListCacheService.RemoveAllWithoutMetadata();
177
+ await DcmtTypeListCacheService.GetAllWithoutMetadataAsync();
178
+ setMruTIDs([...SDKUI_Globals.userSettings.searchSettings.mruTIDs]);
179
+ }, []);
180
+ // Ricerche rapide: invalida la cache delle saved query e ricarica l'elenco del tipo documento corrente
181
+ const refreshSavedQueriesAsync = useCallback(async () => {
182
+ // loadDataSQDsAsync riporta la selezione sulla prima tab: il refresh non deve spostare quella scelta dall'utente
183
+ const sqdMode = currentSQDMode;
184
+ await loadDataSQDsAsync(true, fromDTD?.id ?? currentTID);
185
+ setCurrentSQDMode(sqdMode);
186
+ }, [fromDTD?.id, currentTID, currentSQDMode]);
187
+ // Pannello dei metadati: rilegge dal server i metadati del tipo documento e la definizione della
188
+ // ricerca rapida corrente, con cui il pannello ricostruisce i filtri (i valori digitati vengono persi)
189
+ const refreshSearchQueryPanelAsync = useCallback(async () => {
190
+ const tid = fromDTD?.id ?? currentTID;
191
+ if (!tid)
192
+ return;
193
+ const dtd = await DcmtTypeListCacheService.GetAsync(tid, true, undefined, false, true);
194
+ setFromDTD(dtd);
195
+ // Passare da undefined forza la ricostruzione dei filtri anche quando la query selezionata non cambia
196
+ const sqdToRestore = currentSQD;
197
+ SavedQueryCacheService.Remove();
198
+ await setSQDAsync(undefined);
199
+ // La ricerca di sistema non è in cache: va ricostruita, così recepisce i metadati appena riletti
200
+ await setSQDAsync(sqdToRestore?.id === SYS_ALL_DCMTS_SQD_ID ? await getSysAllDcmtsSQD(tid, false) : sqdToRestore);
201
+ // mruTIDs è tra le dipendenze perché setSQDAsync lo legge
202
+ }, [fromDTD?.id, currentTID, currentSQD, mruTIDs]);
203
+ // Prima di ogni ricerca il pannello rilegge i metadati del tipo documento: si recepisce il descrittore
204
+ // aggiornato, così anche il resto della vista (titoli, badge, form dei metadati) lavora sulla lista corrente
205
+ const handleDcmtTypeReloaded = useCallback((dtd) => {
206
+ setFromDTD(dtd);
207
+ }, []);
155
208
  const onRefreshSearchAsyncDatagrid = async () => {
156
209
  try {
157
210
  if (lastQdSearched) {
@@ -194,29 +247,35 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
194
247
  const isTabletOrMobile = deviceType === DeviceType.TABLET || deviceType === DeviceType.MOBILE;
195
248
  // --- JSX WRAPPERS ---
196
249
  const tmTreeSelectorElement = useMemo(() => _jsx(TMTreeSelectorWrapper, { isMobile: isTabletOrMobile, onSelectedTIDChanged: (tid) => {
250
+ notifySelectedTIDAsync(tid);
197
251
  setCurrentTID(tid);
198
252
  if (tid && mruTIDs.includes(tid))
199
253
  setCurrentMruTID(tid);
200
254
  else
201
255
  setCurrentMruTID(0);
202
- } }), [isTabletOrMobile, mruTIDs]);
256
+ } }), [isTabletOrMobile, mruTIDs, notifySelectedTIDAsync]);
203
257
  const tmRecentsManagerElement = useMemo(() => _jsx(TMRecentsManagerWrapper, { mruTIDs: mruTIDs, currentMruTID: currentMruTID, deviceType: deviceType, onSelectedTID: (tid) => {
258
+ notifySelectedTIDAsync(tid);
204
259
  setCurrentMruTID(tid);
205
260
  setCurrentTID(tid);
206
261
  }, onDeletedTID: (tid) => {
207
262
  let newMruTIDS = removeMruTid(SDKUI_Globals.userSettings.searchSettings.mruTIDs, tid);
208
263
  SDKUI_Globals.userSettings.searchSettings.mruTIDs = newMruTIDS;
209
264
  setMruTIDs(newMruTIDS);
210
- } }), [mruTIDs, currentMruTID, deviceType]);
211
- const tmSearchQueryPanelElement = useMemo(() => _jsx(TMSearchQueryPanelWrapper, { passToArchiveCallback: passToArchiveCallback, isExpertMode: isExpertMode, showBackToResultButton: searchResult.length > 0, fromDTD: fromDTD, SQD: currentSQD, inputMids: inputMids, maxDcmtsToBeReturned: maxDcmtsToBeReturned, onBackToResult: () => { setCurrentSearchView(TMSearchViews.Result); }, onSearchCompleted: handleSearchCompleted, onSqdSaved: async (newSqd) => {
265
+ } }), [mruTIDs, currentMruTID, deviceType, notifySelectedTIDAsync]);
266
+ const tmSearchQueryPanelElement = useMemo(() => _jsx(TMSearchQueryPanelWrapper, { isSearchViewOnScreen: currentSearchView === TMSearchViews.Search, passToArchiveCallback: passToArchiveCallback, isExpertMode: isExpertMode, showBackToResultButton: searchResult.length > 0, fromDTD: fromDTD, SQD: currentSQD, inputMids: inputMids, maxDcmtsToBeReturned: maxDcmtsToBeReturned, onBackToResult: () => { if (onlyShowSearchQueryPanel)
267
+ setShowSearchResults(true); setCurrentSearchView(TMSearchViews.Result); }, onSearchCompleted: handleSearchCompleted, onRefreshRequested: refreshSearchQueryPanelAsync, onDcmtTypeReloaded: handleDcmtTypeReloaded, onSqdSaved: async (newSqd) => {
212
268
  await loadDataSQDsAsync(true, newSqd.masterTID);
213
269
  await setSQDAsync(newSqd);
214
- } }), [fromDTD, showSearchResults, setShowSearchResults, currentSQD, isExpertMode, mruTIDs, searchResult, passToArchiveCallback, inputMids, maxDcmtsToBeReturned, handleSearchCompleted]);
215
- const tmSavedQuerySelectorElement = useMemo(() => _jsxs(TabPanel, { width: "100%", height: "100%", showNavButtons: true, repaintChangesOnly: true, selectedIndex: currentSQDMode, onSelectedIndexChange: (index) => setCurrentSQDMode(index), children: [(currentTID || currentSQD) ? _jsx(Item, { title: fromDTD?.nameLoc, children: _jsx(TMSavedQuerySelectorWrapper, { allowShowSearch: false, items: filteredByTIDSQDs, selectedId: currentSQD?.id, onRefreshData: () => { loadDataSQDsAsync(true); }, onItemClick: (sqd) => {
270
+ } }), [fromDTD, showSearchResults, setShowSearchResults, currentSQD, currentSearchView, isExpertMode, mruTIDs, searchResult, passToArchiveCallback, inputMids, maxDcmtsToBeReturned, handleSearchCompleted, refreshSearchQueryPanelAsync, handleDcmtTypeReloaded, onlyShowSearchQueryPanel]);
271
+ // I due tab delle ricerche rapide nell'ordine in cui compaiono: il primo c'e' solo con un tipo
272
+ // documento o una ricerca rapida correnti. currentSQDMode resta la posizione nell'elenco visibile.
273
+ const sqdTabIds = useMemo(() => (currentTID || currentSQD) ? ['byTID', 'all'] : ['all'], [currentTID, currentSQD]);
274
+ const tmSavedQuerySelectorElement = useMemo(() => _jsxs(TMTabControl, { variant: 'module', style: { height: '100%', width: '100%' }, contentStyle: { display: 'flex', flexDirection: 'column', flex: 1, minHeight: 0 }, selectedId: sqdTabIds[currentSQDMode] ?? sqdTabIds[sqdTabIds.length - 1], onSelectedIdChange: (id) => setCurrentSQDMode(sqdTabIds.indexOf(id)), children: [_jsx(TMTabPanel, { id: 'byTID', label: fromDTD?.nameLoc, visible: !!(currentTID || currentSQD), children: _jsx(TMSavedQuerySelectorWrapper, { allowShowSearch: false, items: filteredByTIDSQDs, selectedId: currentSQD?.id, onRefreshData: () => { loadDataSQDsAsync(true); }, onItemClick: (sqd) => {
216
275
  onSQDItemClick(sqd, setSQDAsync);
217
- }, onDeleted: (sqd) => onSQDDeleted(sqd, sqd.id == currentSQD?.id ? filteredByTIDSQDs.find(o => o.id == 1) : currentSQD, setSQDAsync), refreshFavoriteSavedQueries: refreshFavoriteSavedQueries }) }) : _jsx(_Fragment, {}), _jsx(Item, { title: SDKUI_Localizator.AllFemale, children: _jsx(TMSavedQuerySelectorWrapper, { allowShowSearch: true, items: allSQDs, manageDefault: false, onItemClick: (sqd) => {
276
+ }, onDeleted: (sqd) => onSQDDeleted(sqd, sqd.id == currentSQD?.id ? filteredByTIDSQDs.find(o => o.id == 1) : currentSQD, setSQDAsync), refreshFavoriteSavedQueries: refreshFavoriteSavedQueries }) }), _jsx(TMTabPanel, { id: 'all', label: SDKUI_Localizator.AllFemale, children: _jsx(TMSavedQuerySelectorWrapper, { allowShowSearch: true, items: allSQDs, manageDefault: false, onItemClick: (sqd) => {
218
277
  onSQDItemClick(sqd, setSQDAsync);
219
- }, onDeleted: (sqd) => onSQDDeleted(sqd, sqd.id == currentSQD?.id ? undefined : currentSQD, setSQDAsync), refreshFavoriteSavedQueries: refreshFavoriteSavedQueries }) })] }), [currentSQDMode, currentTID, currentSQD, fromDTD, filteredByTIDSQDs, allSQDs]);
278
+ }, onDeleted: (sqd) => onSQDDeleted(sqd, sqd.id == currentSQD?.id ? undefined : currentSQD, setSQDAsync), refreshFavoriteSavedQueries: refreshFavoriteSavedQueries }) })] }), [currentSQDMode, sqdTabIds, currentTID, currentSQD, fromDTD, filteredByTIDSQDs, allSQDs]);
220
279
  // Returns the current panelLayout from user settings, falling back to an empty object if not present.
221
280
  const getPanelLayoutSetting = () => {
222
281
  return SDKUI_Globals.userSettings.searchSettings.panelLayout ?? {};
@@ -263,7 +322,14 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
263
322
  {
264
323
  id: 'TMRecentsManager',
265
324
  name: SDKUI_Localizator.Shortcuts,
266
- contentOptions: { component: tmRecentsManagerElement, panelContainer: { title: SDKUI_Localizator.Shortcuts, totalItems: mruTIDs.length } },
325
+ contentOptions: {
326
+ component: tmRecentsManagerElement,
327
+ panelContainer: {
328
+ title: SDKUI_Localizator.Shortcuts,
329
+ totalItems: mruTIDs.length,
330
+ onRefresh: refreshRecentsAsync
331
+ }
332
+ },
267
333
  toolbarOptions: { icon: _jsx(IconRecentlyViewed, { fontSize: 24 }), visible: true, orderNumber: 2, isActive: allInitialPanelVisibility['TMRecentsManager'] }
268
334
  },
269
335
  {
@@ -275,11 +341,70 @@ const TMSearch = ({ allTasks = [], getAllTasks, deleteTaskByIdsCallback, addTask
275
341
  {
276
342
  id: 'TMSavedQuerySelector',
277
343
  name: SDK_Localizator.SavedQueries,
278
- contentOptions: { component: tmSavedQuerySelectorElement, panelContainer: { title: SDK_Localizator.SavedQueries } },
344
+ contentOptions: {
345
+ component: tmSavedQuerySelectorElement,
346
+ panelContainer: {
347
+ title: SDK_Localizator.SavedQueries,
348
+ onRefresh: refreshSavedQueriesAsync
349
+ }
350
+ },
279
351
  toolbarOptions: { icon: _jsx(IconSavedQuery, { fontSize: 24 }), visible: true, orderNumber: 4, isActive: allInitialPanelVisibility['TMSavedQuerySelector'] }
280
352
  }
281
- ], [tmTreeSelectorElement, showSearchResults, tmRecentsManagerElement, tmSearchQueryPanelElement, tmSavedQuerySelectorElement, fromDTD, mruTIDs]);
282
- return (_jsxs(_Fragment, { children: [showSearchResults ? _jsx(StyledMultiViewPanel, { "$isVisible": currentSearchView === TMSearchViews.Search, children: _jsx(TMPanelManagerWithPersistenceProvider, { panels: initialPanels, initialVisibility: allInitialPanelVisibility, defaultDimensions: initialPanelDimensions, initialDimensions: initialPanelDimensions, initialMobilePanelId: 'TMRecentsManager', isPersistenceEnabled: !isMobile ? hasSavedLayout() : false, persistPanelStates: !isMobile ? (state) => persistPanelStates(state) : undefined, persistedPanelStates: getPersistedPanelStates(), children: _jsx(TMPanelManagerContainer, { panels: initialPanels, direction: "horizontal", showToolbar: true, minPanelSizePx: !isMobile ? 250 : 150 }) }) }) : tmSearchQueryPanelElement, showSearchResults && _jsx(TMSearchResult, { isVisible: isVisible && currentSearchView === TMSearchViews.Result, context: SearchResultContext.METADATA_SEARCH, searchResults: searchResult, floatingActionConfig: floatingActionConfig, onRefreshAfterAddDcmtToFavs: onRefreshAfterAddDcmtToFavs, openInOffice: openInOffice, onRefreshSearchAsyncDatagrid: onRefreshSearchAsyncDatagrid, onClose: () => { onlyShowSearchQueryPanel ? setShowSearchResults(false) : setCurrentSearchView(TMSearchViews.Search); }, onFileOpened: onFileOpened, onTaskCreateRequest: onTaskCreateRequest, openWGsCopyMoveForm: openWGsCopyMoveForm, editPdfForm: editPdfForm, onOpenPdfEditorRequest: onOpenPdfEditorRequest, openS4TViewer: openS4TViewer, onOpenS4TViewerRequest: onOpenS4TViewerRequest, openFileUploaderPdfEditor: openFileUploaderPdfEditor, passToArchiveCallback: passToArchiveCallback, onSelectedTIDChanged: onCurrentTIDChangedCallback, showTodoDcmtForm: showTodoDcmtForm, showToppyDraggableHelpCenter: showToppyDraggableHelpCenter, toppyHelpCenterUsePortal: toppyHelpCenterUsePortal, onReferenceClick: onReferenceClick, allTasks: allTasks, getAllTasks: getAllTasks, deleteTaskByIdsCallback: deleteTaskByIdsCallback, addTaskCallback: addTaskCallback, editTaskCallback: editTaskCallback, handleNavigateToWGs: handleNavigateToWGs, handleNavigateToDossiers: handleNavigateToDossiers, inputDID: inputDID, formAutoOpen: formAutoOpen, fetchRemoteCertificates: fetchRemoteCertificates, graphometricManager: graphometricManager })] }));
353
+ ], [tmTreeSelectorElement, showSearchResults, tmRecentsManagerElement, tmSearchQueryPanelElement, tmSavedQuerySelectorElement, fromDTD, mruTIDs, refreshRecentsAsync, refreshSavedQueriesAsync]);
354
+ // Quando è visibile solo il pannello di ricerca (es. modale di abbinamento molti a molti) serve
355
+ const singlePanelVisibility = { 'TMSearchQueryPanel': true };
356
+ const singlePanelDimensions = { 'TMSearchQueryPanel': { width: '100%', height: '100%' } };
357
+ const singlePanelDefinition = useMemo(() => [
358
+ {
359
+ id: 'TMSearchQueryPanel',
360
+ name: fromDTD?.nameLoc ?? SDKUI_Localizator.Search_Metadata,
361
+ contentOptions: { component: tmSearchQueryPanelElement },
362
+ toolbarOptions: { icon: _jsx(IconFilter, { fontSize: 24 }), visible: false, orderNumber: 1, isActive: true }
363
+ }
364
+ ], [tmSearchQueryPanelElement, fromDTD]);
365
+ return (_jsxs(_Fragment, { children: [onlyShowSearchQueryPanel
366
+ // Il pannello di ricerca resta montato anche quando sono a schermo i risultati: tornando
367
+ // indietro si ritrova l'ultima ricerca impostata, senza rimontaggi che ne resettano i filtri
368
+ ? _jsx(StyledMultiViewPanel, { $isVisible: !showSearchResults, children: _jsx(TMPanelManagerProvider, { panels: singlePanelDefinition, initialVisibility: singlePanelVisibility, defaultDimensions: singlePanelDimensions, initialDimensions: singlePanelDimensions, initialMobilePanelId: 'TMSearchQueryPanel', children: tmSearchQueryPanelElement }) })
369
+ : _jsx(StyledMultiViewPanel, { $isVisible: currentSearchView === TMSearchViews.Search, children: _jsx(TMPanelManagerWithPersistenceProvider, { panels: initialPanels, initialVisibility: allInitialPanelVisibility, defaultDimensions: initialPanelDimensions, initialDimensions: initialPanelDimensions, initialMobilePanelId: 'TMRecentsManager', isPersistenceEnabled: !isMobile ? hasSavedLayout() : false, persistPanelStates: !isMobile ? (state) => persistPanelStates(state) : undefined, persistedPanelStates: getPersistedPanelStates(), children: _jsx(TMPanelManagerContainer, { panels: initialPanels, direction: "horizontal", showToolbar: true, minPanelSizePx: !isMobile ? 250 : 150 }) }) }), showSearchResults && _jsx(TMSearchResult, { isVisible: isVisible && currentSearchView === TMSearchViews.Result, context: SearchResultContext.METADATA_SEARCH, searchResults: searchResult, floatingActionConfig: floatingActionConfig, onRefreshAfterAddDcmtToFavs: onRefreshAfterAddDcmtToFavs, openInOffice: openInOffice, onRefreshSearchAsyncDatagrid: onRefreshSearchAsyncDatagrid, onClose: () => { if (onlyShowSearchQueryPanel)
370
+ setShowSearchResults(false); setCurrentSearchView(TMSearchViews.Search); }, backCaption: onlyShowSearchQueryPanel ? SDKUI_Localizator.BackToSearch : undefined, onFileOpened: onFileOpened, onTaskCreateRequest: onTaskCreateRequest, openWGsCopyMoveForm: openWGsCopyMoveForm, editPdfForm: editPdfForm, onOpenPdfEditorRequest: onOpenPdfEditorRequest, openS4TViewer: openS4TViewer, onOpenS4TViewerRequest: onOpenS4TViewerRequest, openFileUploaderPdfEditor: openFileUploaderPdfEditor, passToArchiveCallback: passToArchiveCallback, onSelectedTIDChanged: onCurrentTIDChangedCallback, showTodoDcmtForm: showTodoDcmtForm, showToppyDraggableHelpCenter: showToppyDraggableHelpCenter, toppyHelpCenterUsePortal: toppyHelpCenterUsePortal, onReferenceClick: onReferenceClick, allTasks: allTasks, getAllTasks: getAllTasks, deleteTaskByIdsCallback: deleteTaskByIdsCallback, addTaskCallback: addTaskCallback, editTaskCallback: editTaskCallback, handleNavigateToWGs: handleNavigateToWGs, handleNavigateToDossiers: handleNavigateToDossiers, inputDID: inputDID, formAutoOpen: formAutoOpen, fetchRemoteCertificates: fetchRemoteCertificates, graphometricManager: graphometricManager })] }));
371
+ };
372
+ const ENABLE_SEARCH_TABS = false;
373
+ // Ogni tab e' un TMSearch completo e indipendente: TMTabControl li tiene tutti montati, cosi piu ricerche
374
+ // restano vive insieme, ognuna con i suoi tipi documento, i suoi filtri e i suoi risultati.
375
+ const TMSearch = (props) => {
376
+ const { isVisible, inputTID, inputSqdID, inputDID, onlyShowSearchQueryPanel, onCurrentTIDChangedCallback } = props;
377
+ const tabs = useTMTabs({ label: SDKUI_Localizator.Search });
378
+ // Tab attivo leggibile senza rilanciare l'effetto qui sotto a ogni cambio tab
379
+ const activeIdRef = useRef(tabs.activeId);
380
+ activeIdRef.current = tabs.activeId;
381
+ // Titoli correnti leggibili dalla callback senza rigenerarla a ogni rinomina
382
+ const itemsRef = useRef(tabs.items);
383
+ itemsRef.current = tabs.items;
384
+ // Il titolo del tab e' il nome appena selezionato; se un altro tab ha gia' quel titolo si numera
385
+ // tra parentesi a partire da 2: NomeTipoDocumento, NomeTipoDocumento (2), NomeTipoDocumento (3)...
386
+ const setTabTitle = useCallback((id, name) => {
387
+ const used = new Set(itemsRef.current.filter(t => t.id !== id).map(t => t.label));
388
+ let label = name;
389
+ for (let i = 2; used.has(label); i++)
390
+ label = `${name} (${i})`;
391
+ tabs.rename(id, label);
392
+ }, [tabs.rename]);
393
+ // Una richiesta dall'esterno (tipo documento, ricerca rapida, documento) riguarda il tab a video in
394
+ // quel momento: gli altri restano sulla ricerca che stanno svolgendo.
395
+ const [inputsTabId, setInputsTabId] = useState(tabs.activeId);
396
+ useEffect(() => { setInputsTabId(activeIdRef.current); }, [inputTID, inputSqdID, inputDID]);
397
+ // Nella modalita a solo pannello di ricerca (es. abbinamento molti a molti) i tab non servono,
398
+ // cosi come non servono finche' i tab non vengono rilasciati
399
+ if (!ENABLE_SEARCH_TABS || onlyShowSearchQueryPanel)
400
+ return _jsx(TMSearchInstance, { ...props });
401
+ return (_jsx(TMTabControl, { ...tabs.controlProps, contentAnimation: 'none', onTabRename: undefined, variant: 'module', style: { height: '100%', width: '100%' }, contentStyle: { display: 'flex', flex: 1, minHeight: 0, position: 'relative' }, children: tabs.items.map(t => {
402
+ const isActiveTab = t.id === tabs.activeId;
403
+ const hasInputs = t.id === inputsTabId;
404
+ return (_jsx(TMTabPanel, { id: t.id, label: t.label, children: _jsx(TMSearchInstance, { ...props, isVisible: isVisible && isActiveTab, inputTID: hasInputs ? inputTID : undefined, inputSqdID: hasInputs ? inputSqdID : undefined, inputDID: hasInputs ? inputDID : undefined,
405
+ // Il tipo documento corrente lo comunica solo il tab a video
406
+ onCurrentTIDChangedCallback: isActiveTab ? onCurrentTIDChangedCallback : undefined, onSelectedNameChanged: (name) => setTabTitle(t.id, name) }) }, t.id));
407
+ }) }));
283
408
  };
284
409
  export default TMSearch;
285
410
  const TMTreeSelectorWrapper = ({ isMobile, onSelectedTIDChanged }) => {
@@ -298,11 +423,11 @@ const TMRecentsManagerWrapper = ({ mruTIDs, currentMruTID, deviceType, onSelecte
298
423
  onDeletedTID?.(tid);
299
424
  } }));
300
425
  };
301
- const TMSearchQueryPanelWrapper = ({ fromDTD, SQD, isExpertMode, showBackToResultButton, onSearchCompleted, onSqdSaved, onBackToResult, passToArchiveCallback, inputMids, maxDcmtsToBeReturned }) => {
426
+ const TMSearchQueryPanelWrapper = ({ isSearchViewOnScreen, fromDTD, SQD, isExpertMode, showBackToResultButton, onSearchCompleted, onSqdSaved, onBackToResult, passToArchiveCallback, inputMids, maxDcmtsToBeReturned, onRefreshRequested, onDcmtTypeReloaded }) => {
302
427
  const { setPanelVisibilityById, toggleMaximize, countVisibleLeafPanels } = useTMPanelManagerContext();
303
428
  const deviceType = useDeviceType();
304
429
  const isMobile = deviceType === DeviceType.MOBILE;
305
- return (_jsx(TMSearchQueryPanel, { onClosePanel: (!isMobile && countVisibleLeafPanels() > 1) ? () => setPanelVisibilityById('TMSearchQueryPanel', false) : undefined, allowMaximize: !isMobile && countVisibleLeafPanels() > 1, onMaximizePanel: (!isMobile && countVisibleLeafPanels() > 1) ? () => toggleMaximize("TMSearchQueryPanel") : undefined, isExpertMode: isExpertMode, fromDTD: fromDTD, SQD: SQD, inputMids: inputMids, onSearchCompleted: onSearchCompleted, onSqdSaved: onSqdSaved, showBackToResultButton: showBackToResultButton, onBackToResult: onBackToResult, passToArchiveCallback: passToArchiveCallback, maxDcmtsToBeReturned: maxDcmtsToBeReturned }));
430
+ return (_jsx(TMSearchQueryPanel, { isSearchViewOnScreen: isSearchViewOnScreen, onClosePanel: (!isMobile && countVisibleLeafPanels() > 1) ? () => setPanelVisibilityById('TMSearchQueryPanel', false) : undefined, allowMaximize: !isMobile && countVisibleLeafPanels() > 1, onMaximizePanel: (!isMobile && countVisibleLeafPanels() > 1) ? () => toggleMaximize("TMSearchQueryPanel") : undefined, isExpertMode: isExpertMode, fromDTD: fromDTD, SQD: SQD, inputMids: inputMids, onSearchCompleted: onSearchCompleted, onRefreshRequested: onRefreshRequested, onDcmtTypeReloaded: onDcmtTypeReloaded, onSqdSaved: onSqdSaved, showBackToResultButton: showBackToResultButton, onBackToResult: onBackToResult, passToArchiveCallback: passToArchiveCallback, maxDcmtsToBeReturned: maxDcmtsToBeReturned }));
306
431
  };
307
432
  const TMSavedQuerySelectorWrapper = ({ items, selectedId, allowShowSearch, manageDefault, onRefreshData, onItemClick, onDeleted, refreshFavoriteSavedQueries }) => {
308
433
  const { setPanelVisibilityById } = useTMPanelManagerContext();
@@ -1,4 +1,4 @@
1
- import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
1
+ import { Fragment as _Fragment, jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react';
3
3
  import { LayoutModes, DcmtTypeListCacheService, PlatformObjectValidator, MetadataDataTypes, QueryOperators, DataListCacheService, MetadataDataDomains, SDK_Localizator, UserListCacheService } from '@topconsultnpm/sdk-ts';
4
4
  import styled from 'styled-components';
@@ -58,10 +58,12 @@ const TMSearchQueryEditor = ({ qd, dcmtTypesList = [], isExpertMode = SDKUI_Glob
58
58
  const handleItemSelect = useCallback((tid, mid) => {
59
59
  if (currentEditingMID !== mid)
60
60
  setCurrentEditingMID(mid);
61
- if (!focusedTidMid || mid !== focusedTidMid.mid) {
62
- setFocusedTidMid({ tid: tid, mid: mid });
61
+ if (!focusedTidMid || mid !== focusedTidMid.mid || tid !== focusedTidMid.tid) {
62
+ const newFocusedTidMid = { tid: tid, mid: mid };
63
+ setFocusedTidMid(newFocusedTidMid);
64
+ onFocusedMetadataChanged?.(newFocusedTidMid);
63
65
  }
64
- }, [currentEditingMID, focusedTidMid]);
66
+ }, [currentEditingMID, focusedTidMid, onFocusedMetadataChanged]);
65
67
  const handleAdvancedMenuClick = useCallback((e) => {
66
68
  if (e.button === AdvancedMenuButtons.MakeEditable && e.mid) {
67
69
  addOrRemoveEditableList(e.mid);
@@ -373,7 +375,7 @@ const WhereItemRow = React.memo(({ whereItem, index, dcmtTypesList, isExpertMode
373
375
  };
374
376
  // --- Rendering ---
375
377
  if (isCompactView) {
376
- return (_jsx(StyledMetadataListItem, { id: `wi-item-${whereItem.mid}`, onClick: () => onItemSelect(whereItem.tid, whereItem.mid), onFocus: () => onItemSelect(whereItem.tid, whereItem.mid), "$backgroundColor": !PlatformObjectValidator.WhereItemHasValues(whereItem) ? `${TMColors.primary}66` : 'rgba(236, 202, 156, 1)', "$hoverColor": !PlatformObjectValidator.WhereItemHasValues(whereItem) ? `${TMColors.primary}33` : 'rgba(236, 202, 156, .5)', children: _jsx(TMSearchWhereItemCard, { isSelected: isSelected, index: index, whereItem: whereItem, showEditor: currentEditingMID === whereItem.mid, isEditableList: isEditable, queryParamsDynDataList: queryParamsDynDataList, onWhereItemChange: onItemChange, onHideEditor: onHideMobileEditor, onCascadeRefreshDynDataLists: onCascadeRefreshDynDataLists, onCascadeUpdateMIDs: onCascadeUpdateMIDs, updateIsModalOpen: updateIsModalOpen }) }));
378
+ return (_jsx(StyledMetadataListItem, { id: `wi-item-${whereItem.mid}`, onClick: () => onItemSelect(whereItem.tid, whereItem.mid), onFocus: () => onItemSelect(whereItem.tid, whereItem.mid), $backgroundColor: !PlatformObjectValidator.WhereItemHasValues(whereItem) ? `${TMColors.primary}66` : 'rgba(236, 202, 156, 1)', $hoverColor: !PlatformObjectValidator.WhereItemHasValues(whereItem) ? `${TMColors.primary}33` : 'rgba(236, 202, 156, .5)', children: _jsx(TMSearchWhereItemCard, { isSelected: isSelected, index: index, whereItem: whereItem, showEditor: currentEditingMID === whereItem.mid, isEditableList: isEditable, queryParamsDynDataList: queryParamsDynDataList, onWhereItemChange: onItemChange, onHideEditor: onHideMobileEditor, onCascadeRefreshDynDataLists: onCascadeRefreshDynDataLists, onCascadeUpdateMIDs: onCascadeUpdateMIDs, updateIsModalOpen: updateIsModalOpen }) }));
377
379
  }
378
380
  return (_jsxs(React.Fragment, { children: [_jsx("div", { id: `wi-item-${whereItem.mid}`, style: { gridColumn: 1 }, children: _jsx(TMMidViewer, { color: TMColors.primaryColor, isMetadataSelected: isSelected, showIcon: true, tid_mid: { tid: whereItem?.tid, mid: whereItem?.mid, aliasTID: whereItem?.alias } }) }), _jsx("div", { style: { gridColumn: 2, paddingLeft: '5px', paddingRight: '5px' }, children: _jsx(TMDropDownMenu, { backgroundColor: colorOperator, color: getOperatorColor(), items: queryOperatorsItems, content: _jsx(StyledItemWrapper, { children: LocalizeQueryOperators(whereItem.operator) }) }) }), _jsxs("div", { style: { gridColumn: 3, position: 'relative' }, onClick: () => onItemSelect(whereItem.tid, whereItem.mid), onFocus: () => onItemSelect(whereItem.tid, whereItem.mid), children: [_jsx(TMSearchWhereItemEditor, { isSelected: isSelected, openChooserBySingleClick: !isSelected, whereItem: whereItem, index: index, isEditableList: isEditable, queryParamsDynDataList: queryParamsDynDataList, onValueChanged: (values) => {
379
381
  onItemChange({ ...whereItem, value1: values[0], value2: values[1] });
@@ -1,6 +1,7 @@
1
1
  import React from 'react';
2
2
  import { DcmtTypeDescriptor, QueryDescriptor, SavedQueryDescriptor, SearchResultDescriptor } from '@topconsultnpm/sdk-ts';
3
3
  interface ITMSearchQueryPanelProps {
4
+ isSearchViewOnScreen?: boolean;
4
5
  fromDTD?: DcmtTypeDescriptor;
5
6
  SQD?: SavedQueryDescriptor;
6
7
  isExpertMode?: boolean;
@@ -21,6 +22,9 @@ interface ITMSearchQueryPanelProps {
21
22
  value: string;
22
23
  }>, tid?: number) => void;
23
24
  maxDcmtsToBeReturned?: number;
25
+ onRefreshRequested?: () => Promise<void>;
26
+ /** Notifica il tipo documento riletto dal server prima di ogni ricerca, così il chiamante allinea il proprio descrittore */
27
+ onDcmtTypeReloaded?: (dtd: DcmtTypeDescriptor) => void;
24
28
  }
25
29
  declare const TMSearchQueryPanel: React.FunctionComponent<ITMSearchQueryPanelProps>;
26
30
  export default TMSearchQueryPanel;
@@ -1,4 +1,4 @@
1
- import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
1
+ import { Fragment as _Fragment, jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { useCallback, useEffect, useMemo, useRef, useState } from 'react';
3
3
  import { PlatformObjectValidator, QueryDescriptor, WhereItem, SDK_Localizator, SelectItemVisibilities, SDK_Globals, SavedQueryCacheService, SearchEngine, QueryOperators, AccessLevelsEx, AccessLevels } from '@topconsultnpm/sdk-ts';
4
4
  import styled from 'styled-components';
@@ -24,11 +24,9 @@ import TMToppyMessage from '../../../helper/TMToppyMessage';
24
24
  import TMMetadataSorterForm from './TMMetadataSorterForm';
25
25
  import TMMetadataOutputForm from './TMMetadataOutputForm';
26
26
  import TMTooltip from '../../base/TMTooltip';
27
- const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SDKUI_Globals.userSettings.advancedSettings.expertMode === 1, SQD, inputMids, onSearchCompleted, onSqdSaved, onBack, onClosePanel, allowMaximize = true, onMaximizePanel, onBackToResult, passToArchiveCallback, maxDcmtsToBeReturned }) => {
27
+ const TMSearchQueryPanel = ({ isSearchViewOnScreen = true, fromDTD, showBackToResultButton, isExpertMode = SDKUI_Globals.userSettings.advancedSettings.expertMode === 1, SQD, inputMids, onSearchCompleted, onSqdSaved, onBack, onClosePanel, allowMaximize = true, onMaximizePanel, onBackToResult, passToArchiveCallback, maxDcmtsToBeReturned, onRefreshRequested, onDcmtTypeReloaded }) => {
28
28
  const [confirmQueryParams, ConfirmQueryParamsDialog] = useQueryParametersDialog();
29
29
  const [qd, setQd] = useState();
30
- const [shouldSearch, setShouldSearch] = useState(false);
31
- const [isQueryPanelActive, setIsQueryPanelActive] = useState(false);
32
30
  const [lastQdParams, setLastQdParams] = useState([]);
33
31
  const [dcmtTypesList, setDcmtTypesList] = useState([]);
34
32
  const [showSqdForm, setShowSqdForm] = useState(false);
@@ -44,10 +42,32 @@ const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SD
44
42
  const deviceType = useDeviceType();
45
43
  const isMobile = deviceType === DeviceType.MOBILE;
46
44
  let initialMaxItems = deviceType === DeviceType.MOBILE ? 8 : 12;
45
+ const tmPanelRef = useRef(null);
46
+ // Contenitore del form: l'Invio avvia la ricerca solo se il focus si trova al suo interno
47
+ const contentRef = useRef(null);
48
+ // Passando nella vista risultati si prenota il focus, che verrà ripreso al rientro nella ricerca
49
+ const shouldRefocusOnReturnRef = useRef(false);
47
50
  const appliedInputMidsRef = useRef(null);
48
51
  const pendingMidsRef = useRef(null);
49
- // Flag "accoda": impostato dall'azione secondaria del bottone Ricerca, consumato in executeSearch
50
- const appendNextSearchRef = useRef(false);
52
+ // Impedisce ricerche sovrapposte (doppio Invio, o Invio mentre la precedente e' ancora in corso)
53
+ const isSearchingRef = useRef(false);
54
+ // Snapshot letti da runSearch al momento dell'esecuzione: evitano di cercare con dati stantii
55
+ const qdRef = useRef(undefined);
56
+ const showAdvancedSearchRef = useRef(false);
57
+ const searchAsyncRef = useRef();
58
+ const reloadMetadataAsyncRef = useRef();
59
+ // Tornando dalla vista risultati il pannello dei metadati di ricerca riprende il focus,
60
+ // così è lui quello evidenziato: prendendo il focus gli altri pannelli ricevono l'onBlur e si disattivano
61
+ useEffect(() => {
62
+ if (!isSearchViewOnScreen) {
63
+ shouldRefocusOnReturnRef.current = true;
64
+ return;
65
+ }
66
+ if (!shouldRefocusOnReturnRef.current)
67
+ return;
68
+ shouldRefocusOnReturnRef.current = false;
69
+ tmPanelRef.current?.focusPanel();
70
+ }, [isSearchViewOnScreen]);
51
71
  useEffect(() => {
52
72
  if (!SQD)
53
73
  return;
@@ -120,39 +140,6 @@ const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SD
120
140
  setQd({ ...qd, where: newWhere });
121
141
  setShowAllMdWhere(true);
122
142
  }, [qd, fromDTD, inputMids]);
123
- // Eseguire la ricerca quando shouldSearch è true e qd è definito
124
- useEffect(() => {
125
- if (shouldSearch && qd) {
126
- const executeSearch = async () => {
127
- // Legge e consuma il flag "accoda" impostato dall'azione secondaria del bottone Ricerca
128
- const append = appendNextSearchRef.current;
129
- appendNextSearchRef.current = false;
130
- await searchAsync(qd, showAdvancedSearch, append);
131
- setShouldSearch(false); // Resetta il trigger dopo la ricerca
132
- };
133
- executeSearch();
134
- }
135
- }, [shouldSearch, qd, showAdvancedSearch]);
136
- // Se il pannello è attivo e non ci sono modali aperti, rimuove il focus e avvia la ricerca
137
- useEffect(() => {
138
- const handleKeyDown = (e) => {
139
- if (isQueryPanelActive && !modalIsOpen) {
140
- if (e.key === 'Enter') {
141
- e.preventDefault();
142
- // Disattiva l'elemento attivo per forzare l'onBlur
143
- if (document.activeElement instanceof HTMLElement) {
144
- document.activeElement.blur();
145
- }
146
- // Attiva il flag di ricerca. L'useEffect sopra gestirà l'attesa di qd.
147
- setShouldSearch(true);
148
- }
149
- }
150
- };
151
- window.addEventListener('keydown', handleKeyDown);
152
- return () => {
153
- window.removeEventListener('keydown', handleKeyDown);
154
- };
155
- }, [isQueryPanelActive, modalIsOpen]);
156
143
  const setDataAsync = async (sqd) => {
157
144
  let newSqd = (sqd?.id == 1) ? sqd : await SavedQueryCacheService.GetAsync(sqd?.id);
158
145
  let newQd = SearchEngine.NormalizeQueryDescriptor(newSqd?.qd);
@@ -184,11 +171,92 @@ const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SD
184
171
  let results = [];
185
172
  if (searchResult?.result)
186
173
  results.push(searchResult?.result);
187
- // Before notifying onSearchComplete, let's set the panel to NOT active
188
- setIsQueryPanelActive(false);
189
174
  onSearchCompleted?.(results, searchResult?.qd, append);
190
175
  }
191
176
  };
177
+ // Tra l'apertura della ricerca e il click su Ricerca la lista dei metadati del tipo documento può essere
178
+ // cambiata (metadati aggiunti o rimossi lato amministrazione): prima di cercare si rileggono dal server.
179
+ // I valori digitati restano, mentre i filtri sui metadati non più disponibili vengono scartati.
180
+ // Restituisce il qd con cui eseguire la ricerca.
181
+ const reloadMetadataAsync = async (qdInput) => {
182
+ if (!qdInput?.from?.tid)
183
+ return qdInput;
184
+ let dcmtTypes;
185
+ try {
186
+ TMSpinner.show({ description: `${SDKUI_Localizator.Loading} ...`, backgroundColor: 'transparent' });
187
+ dcmtTypes = await getDcmtTypesByQdAsync(qdInput, true);
188
+ }
189
+ finally {
190
+ TMSpinner.hide();
191
+ }
192
+ // Rilettura non riuscita: si cerca con i metadati che si hanno, senza scartare nulla
193
+ if (dcmtTypes.length <= 0)
194
+ return qdInput;
195
+ setDcmtTypesList(dcmtTypes);
196
+ const reloadedFromDTD = dcmtTypes.find(o => o.id === qdInput.from?.tid);
197
+ if (reloadedFromDTD)
198
+ onDcmtTypeReloaded?.(reloadedFromDTD);
199
+ const { qd: newQd, removedCount } = dropUnavailableMetadataFromQd(qdInput, dcmtTypes);
200
+ if (removedCount <= 0)
201
+ return qdInput;
202
+ setQd(newQd);
203
+ return newQd;
204
+ };
205
+ // Allineati a ogni render: runSearch li legge quando esegue, non quando viene creata
206
+ qdRef.current = qd;
207
+ showAdvancedSearchRef.current = showAdvancedSearch;
208
+ searchAsyncRef.current = searchAsync;
209
+ reloadMetadataAsyncRef.current = reloadMetadataAsync;
210
+ // Unico punto di avvio della ricerca: bottone Ricerca, Ricerca e accoda e tasto Invio passano tutti da qui
211
+ const runSearch = useCallback((append) => {
212
+ if (isSearchingRef.current)
213
+ return;
214
+ isSearchingRef.current = true;
215
+ // Toglie il focus per far committare il valore del campo in editing
216
+ if (document.activeElement instanceof HTMLElement)
217
+ document.activeElement.blur();
218
+ // Alcuni editor committano il valore in modo asincrono: si attende un tick prima di leggere il qd definitivo
219
+ setTimeout(async () => {
220
+ try {
221
+ // I metadati si rileggono a ogni ricerca: si cerca sempre sulla lista aggiornata
222
+ const qdToSearch = await reloadMetadataAsyncRef.current?.(qdRef.current) ?? qdRef.current;
223
+ await searchAsyncRef.current?.(qdToSearch, showAdvancedSearchRef.current, append);
224
+ }
225
+ catch (ex) {
226
+ TMExceptionBoxManager.show({ exception: ex });
227
+ }
228
+ finally {
229
+ isSearchingRef.current = false;
230
+ }
231
+ }, 0);
232
+ }, []);
233
+ // I dialoghi (TMModal/chooser) escono da contentRef perche' DevExtreme Popup li rende in un portale su document.body:
234
+ // il controllo di contenimento li esclude gia'. Questi flag coprono il caso in cui il focus sia sul contenitore del pannello.
235
+ // NB: si usano solo flag locali affidabili, non modalIsOpen, che resterebbe a true se un chooser venisse smontato senza onClose.
236
+ const isAnyDialogOpen = showFiltersConfig || showOutputConfig || showMetadataSorterForm || showSqdForm || showDistinctValuesPanel;
237
+ // L'Invio avvia SEMPRE la ricerca quando il focus e' nel form di ricerca (o sul pannello che lo contiene).
238
+ // Il criterio e' il contenimento nel DOM, non uno stato di "pannello attivo" che puo' desincronizzarsi.
239
+ useEffect(() => {
240
+ const handleKeyDown = (e) => {
241
+ if (e.key !== 'Enter' || e.repeat)
242
+ return;
243
+ if (isAnyDialogOpen)
244
+ return;
245
+ const content = contentRef.current;
246
+ const target = e.target;
247
+ if (!content || !target)
248
+ return;
249
+ const isInsideForm = content.contains(target);
250
+ // Al rientro dai risultati il focus e' sul contenitore del pannello, che e' antenato del form
251
+ const isPanelContainer = target !== document.body && target !== document.documentElement && target.contains(content);
252
+ if (!isInsideForm && !isPanelContainer)
253
+ return;
254
+ e.preventDefault();
255
+ runSearch(false);
256
+ };
257
+ window.addEventListener('keydown', handleKeyDown);
258
+ return () => { window.removeEventListener('keydown', handleKeyDown); };
259
+ }, [isAnyDialogOpen, runSearch]);
192
260
  const updateIsModalOpen = useCallback((isOpen) => {
193
261
  setModalIsOpen(isOpen);
194
262
  }, []);
@@ -215,36 +283,15 @@ const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SD
215
283
  }
216
284
  }
217
285
  };
218
- const handleSearchButtonClick = useCallback(async () => {
219
- // Propagazione blur
220
- if (document.activeElement instanceof HTMLElement) {
221
- document.activeElement.blur();
222
- }
223
- // Ricerca normale: azzera l'eventuale flag accoda e avvia
224
- appendNextSearchRef.current = false;
225
- setShouldSearch(true);
226
- }, []);
227
- const handleSearchAndAppendClick = useCallback(() => {
228
- // Propagazione blur
229
- if (document.activeElement instanceof HTMLElement) {
230
- document.activeElement.blur();
231
- }
232
- // Ricerca e accoda: imposta il flag consumato da executeSearch
233
- appendNextSearchRef.current = true;
234
- setShouldSearch(true);
235
- }, []);
286
+ const handleSearchButtonClick = useCallback(() => { runSearch(false); }, [runSearch]);
287
+ const handleSearchAndAppendClick = useCallback(() => { runSearch(true); }, [runSearch]);
236
288
  const searchButtonSecondaryActions = useMemo(() => [{
237
289
  name: SDKUI_Localizator.SearchAndAppend,
238
290
  icon: _jsx(IconSearch, {}),
239
291
  onClick: handleSearchAndAppendClick
240
292
  }], [handleSearchAndAppendClick]);
241
293
  const handleQdChanged = useCallback((newQd) => {
242
- if (!deepCompare(qd, newQd)) {
243
- setQd(newQd);
244
- }
245
- }, []);
246
- const handlePanelActiveChanged = useCallback((isActive) => {
247
- setIsQueryPanelActive(isActive);
294
+ setQd(prev => deepCompare(prev, newQd) ? prev : newQd);
248
295
  }, []);
249
296
  const handleAdvancedMenuClick = useCallback((e) => {
250
297
  if (e.button === AdvancedMenuButtons.DistinctValues) {
@@ -342,10 +389,10 @@ const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SD
342
389
  return false;
343
390
  return qd?.orderBy && qd.orderBy.length > 0;
344
391
  }, [showAdvancedSearch, qd?.orderBy]);
345
- return (_jsxs(_Fragment, { children: [_jsxs(TMPanel, { title: fromDTD?.nameLoc ?? SDKUI_Localizator.Search_Metadata, allowMaximize: allowMaximize, onMaximize: onMaximizePanel, onHeaderDoubleClick: onMaximizePanel, onBack: onBack, onActiveChanged: handlePanelActiveChanged, toolbar: _jsx(_Fragment, { children: (SQD && !showSqdForm) ?
346
- _jsx(ContextMenu, { items: contextMenuItems, trigger: "left", children: _jsx(TMButton, { btnStyle: 'icon', caption: 'Altro', icon: _jsx(IconMenuVertical, { color: 'white' }), showTooltip: false, onClick: () => setIsQueryPanelActive(true) }) })
392
+ return (_jsxs(_Fragment, { children: [_jsxs(TMPanel, { ref: tmPanelRef, title: fromDTD?.nameLoc ?? SDKUI_Localizator.Search_Metadata, allowMaximize: allowMaximize, onMaximize: onMaximizePanel, onHeaderDoubleClick: onMaximizePanel, onBack: onBack, onRefresh: (!SQD || showSqdForm) ? undefined : onRefreshRequested, toolbar: _jsx(_Fragment, { children: (SQD && !showSqdForm) ?
393
+ _jsx(ContextMenu, { items: contextMenuItems, trigger: "left", children: _jsx(TMButton, { btnStyle: 'icon', caption: 'Altro', icon: _jsx(IconMenuVertical, { color: 'white' }), showTooltip: false }) })
347
394
  : _jsx(_Fragment, {}) }), children: [_jsx(ConfirmQueryParamsDialog, {}), SQD
348
- ? _jsxs("div", { onContextMenu: (e) => e.preventDefault(), style: { height: '100%', width: '100%', position: 'relative', display: showSqdForm ? 'none' : 'flex', flexDirection: 'column', gap: 5 }, children: [showAdvancedSearch
395
+ ? _jsxs("div", { ref: contentRef, onContextMenu: (e) => e.preventDefault(), style: { height: '100%', width: '100%', position: 'relative', display: showSqdForm ? 'none' : 'flex', flexDirection: 'column', gap: 5 }, children: [showAdvancedSearch
349
396
  ? _jsx(TMQueryEditor, { formMode: FormModes.Update, showToolbar: false, inputData: qd, validateSelect: true, showApply: false, onQDChanged: handleQdChanged, updateIsModalOpen: updateIsModalOpen })
350
397
  : _jsx(TMSearchQueryEditor, { qd: qd, dcmtTypesList: dcmtTypesList, isExpertMode: isExpertMode, showAllMdWhere: showAllMdWhere, onQdChanged: handleQdChanged, onFocusedMetadataChanged: setFocusedTidMid, onAdvancedMenuClick: handleAdvancedMenuClick, updateIsModalOpen: updateIsModalOpen }), shouldShowOutputBadges && qd?.select && qd.select.length > 0 && (_jsxs(StyledSelectBadgesContainer, { children: [_jsxs(StyledSelectLabel, { children: [SDK_Localizator.QuerySelect, ":"] }), _jsx(StyledSelectBadgesWrapper, { children: (() => {
351
398
  const selectItems = qd.select ?? [];
@@ -403,6 +450,33 @@ const TMSearchQueryPanel = ({ fromDTD, showBackToResultButton, isExpertMode = SD
403
450
  } })] }));
404
451
  };
405
452
  export default TMSearchQueryPanel;
453
+ /** Scarta dal qd filtri, colonne e ordinamenti sui metadati non più esistenti o non più accessibili, in base
454
+ * alla lista dei metadati appena riletta dal server. I valori digitati su quelli ancora presenti si mantengono. */
455
+ const dropUnavailableMetadataFromQd = (qdInput, dcmtTypes) => {
456
+ const metadataOf = (tid) => dcmtTypes.find(o => o.id === tid)?.metadata;
457
+ // Un tipo documento non riletto non è verificabile: i suoi item si mantengono così come sono.
458
+ // Sui metadati di sistema si verifica solo l'esistenza: i loro permessi non li rendono inutilizzabili.
459
+ const isStillAvailable = (tid, mid, isUsable) => {
460
+ const metadata = metadataOf(tid);
461
+ if (!metadata || metadata.length <= 0 || mid == undefined)
462
+ return true;
463
+ const md = metadata.find(o => o.id === mid);
464
+ if (!md)
465
+ return false;
466
+ return md.isSystem == 1 || isUsable(md);
467
+ };
468
+ const canSearch = (md) => md.perm?.canSearch != AccessLevels.No;
469
+ const canOutput = (md) => !(md.perm?.canView == AccessLevels.No && md.perm?.canUpdate == AccessLevels.No);
470
+ const where = qdInput.where?.filter(o => isStillAvailable(o.tid, o.mid, canSearch)) ?? [];
471
+ const select = qdInput.select?.filter(o => isStillAvailable(o.tid, o.mid, canOutput)) ?? [];
472
+ const orderBy = qdInput.orderBy?.filter(o => isStillAvailable(o.tid, o.mid, canOutput)) ?? [];
473
+ const removedCount = ((qdInput.where?.length ?? 0) - where.length)
474
+ + ((qdInput.select?.length ?? 0) - select.length)
475
+ + ((qdInput.orderBy?.length ?? 0) - orderBy.length);
476
+ let qd = new QueryDescriptor();
477
+ qd.init({ ...qdInput, where: where, select: select, orderBy: orderBy });
478
+ return { qd: qd, removedCount: removedCount };
479
+ };
406
480
  const searchByQdAsync = async (qdInput, searchParams) => {
407
481
  let result;
408
482
  let qdSearch;