@cloud-ru/ds-uikit-product-header 1.5.4-preview-65417497.0 → 2.0.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 (225) hide show
  1. package/CHANGELOG.md +17 -0
  2. package/README.md +89 -89
  3. package/dist/cjs/components/HeaderButton/HeaderButton.d.ts +1 -0
  4. package/dist/cjs/components/HeaderLayout/HeaderLayout.d.ts +6 -0
  5. package/dist/cjs/components/Logo/Logo.d.ts +7 -0
  6. package/dist/cjs/components/MainMenu/MainMenu.js +9 -6
  7. package/dist/cjs/components/MainMenu/helperComponents/Banners/MenuBanner.js +1 -1
  8. package/dist/cjs/components/MainMenu/helperComponents/Content/Content.d.ts +6 -0
  9. package/dist/cjs/components/MainMenu/helperComponents/Content/Content.js +35 -11
  10. package/dist/cjs/components/MainMenu/helperComponents/Content/cardsContext.d.ts +20 -0
  11. package/dist/cjs/components/MainMenu/helperComponents/Content/cardsContext.js +17 -0
  12. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/ContentToolbar/ContentToolbar.d.ts +9 -0
  13. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/SortableGroup.d.ts +23 -4
  14. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/SortableGroup.js +38 -10
  15. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupCards.d.ts +7 -4
  16. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupCards.js +8 -4
  17. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupDragHandle.d.ts +2 -0
  18. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupHeader.d.ts +3 -1
  19. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupHeader.js +6 -4
  20. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupSkeleton.d.ts +1 -0
  21. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategory.d.ts +9 -4
  22. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategory.js +17 -12
  23. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategoryTitle.d.ts +8 -3
  24. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategoryTitle.js +24 -18
  25. package/dist/cjs/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/styles.module.css +17 -0
  26. package/dist/cjs/components/MainMenu/helperComponents/Content/hooks/useContentSegmentsSortable.js +4 -2
  27. package/dist/cjs/components/MainMenu/helperComponents/Content/hooks/useProgressiveCount.d.ts +12 -0
  28. package/dist/cjs/components/MainMenu/helperComponents/Content/hooks/useProgressiveCount.js +39 -0
  29. package/dist/cjs/components/MainMenu/helperComponents/Content/hooks/useSegmentDnd.d.ts +4 -4
  30. package/dist/cjs/components/MainMenu/helperComponents/Content/hooks/useSegmentDnd.js +3 -3
  31. package/dist/cjs/components/MainMenu/helperComponents/Content/styles.module.css +16 -0
  32. package/dist/cjs/components/MainMenu/helperComponents/Favorites/Favorites.d.ts +4 -4
  33. package/dist/cjs/components/MainMenu/helperComponents/Favorites/Favorites.js +10 -33
  34. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/Content.d.ts +31 -0
  35. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/Content.js +43 -0
  36. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/EmptyState/EmptyState.d.ts +4 -1
  37. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/EmptyState/EmptyState.js +4 -2
  38. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/FavoritesList.d.ts +21 -0
  39. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/FavoritesList.js +31 -0
  40. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/FavoritesReorderList.d.ts +24 -0
  41. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/FavoritesReorderList.js +36 -0
  42. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/RecentList.d.ts +24 -0
  43. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/RecentList.js +31 -0
  44. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/SortableFavoriteCard.d.ts +9 -3
  45. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/SortableFavoriteCard.js +5 -3
  46. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/index.d.ts +1 -1
  47. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/index.js +1 -1
  48. package/dist/cjs/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesAutoSwitch.d.ts +16 -0
  49. package/dist/cjs/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesAutoSwitch.js +28 -0
  50. package/dist/cjs/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesReorder.d.ts +30 -0
  51. package/dist/cjs/components/MainMenu/helperComponents/Favorites/hooks/{useFavoritesDnd.js → useFavoritesReorder.js} +21 -22
  52. package/dist/cjs/components/MainMenu/helperComponents/Favorites/styles.module.css +9 -3
  53. package/dist/cjs/components/MainMenu/helperComponents/Favorites/utils.d.ts +2 -2
  54. package/dist/cjs/components/MainMenu/helperComponents/MenuBottom/MenuBottom.d.ts +2 -0
  55. package/dist/cjs/components/MainMenu/helperComponents/MenuDesktop/MenuDesktop.d.ts +1 -1
  56. package/dist/cjs/components/MainMenu/helperComponents/MenuDesktop/MenuDesktop.js +7 -7
  57. package/dist/cjs/components/MainMenu/helperComponents/MenuDesktop/styles.module.css +0 -6
  58. package/dist/cjs/components/MainMenu/helperComponents/MenuHeaderBrand/MenuHeaderBrand.d.ts +3 -0
  59. package/dist/cjs/components/MainMenu/helperComponents/MenuMobile/MenuMobile.d.ts +1 -1
  60. package/dist/cjs/components/MainMenu/helperComponents/MenuMobile/MenuMobile.js +5 -6
  61. package/dist/cjs/components/MainMenu/helperComponents/MenuMobile/styles.module.css +0 -7
  62. package/dist/cjs/components/MainMenu/helperComponents/MountAnimation/MountAnimation.d.ts +1 -1
  63. package/dist/cjs/components/MainMenu/helperComponents/MountAnimation/MountAnimation.js +4 -1
  64. package/dist/cjs/components/MainMenu/helperComponents/ServiceCard/ServiceCard.d.ts +30 -6
  65. package/dist/cjs/components/MainMenu/helperComponents/ServiceCard/ServiceCard.js +30 -21
  66. package/dist/cjs/components/MainMenu/helperComponents/ServiceCard/styles.module.css +6 -1
  67. package/dist/cjs/components/MainMenu/hooks/useMainMenuDnd.d.ts +6 -4
  68. package/dist/cjs/components/MainMenu/hooks/useMainMenuDnd.js +4 -6
  69. package/dist/cjs/components/MainMenu/hooks/useMenuItems.js +12 -7
  70. package/dist/cjs/components/MainMenu/types.d.ts +31 -1
  71. package/dist/cjs/components/MainMenu/utils/filterLinksGroupsFuzzy.d.ts +5 -0
  72. package/dist/cjs/components/MainMenu/utils/filterLinksGroupsFuzzy.js +21 -7
  73. package/dist/cjs/components/MainMenu/utils/flatLinksGroups.d.ts +2 -0
  74. package/dist/cjs/components/MainMenu/utils/flatLinksGroups.js +5 -0
  75. package/dist/cjs/components/MainMenu/utils/resolveInnerLinksByIds.d.ts +2 -2
  76. package/dist/cjs/components/MainMenu/utils/resolveInnerLinksByIds.js +2 -4
  77. package/dist/cjs/components/PathBreadcrumbs/PathBreadcrumbs.d.ts +1 -0
  78. package/dist/cjs/components/UserMenu/UserMenu.d.ts +12 -0
  79. package/dist/cjs/components/UserMenu/UserMenu.js +1 -1
  80. package/dist/cjs/components/UserMenu/types.d.ts +7 -0
  81. package/dist/cjs/style.css +48 -17
  82. package/dist/cjs/utils/noop.d.ts +1 -0
  83. package/dist/cjs/utils/noop.js +5 -0
  84. package/dist/esm/components/HeaderButton/HeaderButton.d.ts +1 -0
  85. package/dist/esm/components/HeaderLayout/HeaderLayout.d.ts +6 -0
  86. package/dist/esm/components/Logo/Logo.d.ts +7 -0
  87. package/dist/esm/components/MainMenu/MainMenu.js +10 -7
  88. package/dist/esm/components/MainMenu/helperComponents/Banners/MenuBanner.js +1 -1
  89. package/dist/esm/components/MainMenu/helperComponents/Content/Content.d.ts +6 -0
  90. package/dist/esm/components/MainMenu/helperComponents/Content/Content.js +37 -13
  91. package/dist/esm/components/MainMenu/helperComponents/Content/cardsContext.d.ts +20 -0
  92. package/dist/esm/components/MainMenu/helperComponents/Content/cardsContext.js +13 -0
  93. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/ContentToolbar/ContentToolbar.d.ts +9 -0
  94. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/SortableGroup.d.ts +23 -4
  95. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/SortableGroup.js +37 -9
  96. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupCards.d.ts +7 -4
  97. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupCards.js +9 -5
  98. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupDragHandle.d.ts +2 -0
  99. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupHeader.d.ts +3 -1
  100. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupHeader.js +5 -3
  101. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupSkeleton.d.ts +1 -0
  102. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategory.d.ts +9 -4
  103. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategory.js +18 -13
  104. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategoryTitle.d.ts +8 -3
  105. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategoryTitle.js +25 -19
  106. package/dist/esm/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/styles.module.css +17 -0
  107. package/dist/esm/components/MainMenu/helperComponents/Content/hooks/useContentSegmentsSortable.js +4 -2
  108. package/dist/esm/components/MainMenu/helperComponents/Content/hooks/useProgressiveCount.d.ts +12 -0
  109. package/dist/esm/components/MainMenu/helperComponents/Content/hooks/useProgressiveCount.js +35 -0
  110. package/dist/esm/components/MainMenu/helperComponents/Content/hooks/useSegmentDnd.d.ts +4 -4
  111. package/dist/esm/components/MainMenu/helperComponents/Content/hooks/useSegmentDnd.js +3 -3
  112. package/dist/esm/components/MainMenu/helperComponents/Content/styles.module.css +16 -0
  113. package/dist/esm/components/MainMenu/helperComponents/Favorites/Favorites.d.ts +4 -4
  114. package/dist/esm/components/MainMenu/helperComponents/Favorites/Favorites.js +12 -35
  115. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/Content.d.ts +31 -0
  116. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/Content.js +40 -0
  117. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/EmptyState/EmptyState.d.ts +4 -1
  118. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/EmptyState/EmptyState.js +3 -1
  119. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/FavoritesList.d.ts +21 -0
  120. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/FavoritesList.js +25 -0
  121. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/FavoritesReorderList.d.ts +24 -0
  122. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/FavoritesReorderList.js +30 -0
  123. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/RecentList.d.ts +24 -0
  124. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/RecentList.js +25 -0
  125. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/SortableFavoriteCard.d.ts +9 -3
  126. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/SortableFavoriteCard.js +5 -3
  127. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/index.d.ts +1 -1
  128. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/index.js +1 -1
  129. package/dist/esm/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesAutoSwitch.d.ts +16 -0
  130. package/dist/esm/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesAutoSwitch.js +25 -0
  131. package/dist/esm/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesReorder.d.ts +30 -0
  132. package/dist/esm/components/MainMenu/helperComponents/Favorites/hooks/{useFavoritesDnd.js → useFavoritesReorder.js} +21 -22
  133. package/dist/esm/components/MainMenu/helperComponents/Favorites/styles.module.css +9 -3
  134. package/dist/esm/components/MainMenu/helperComponents/Favorites/utils.d.ts +2 -2
  135. package/dist/esm/components/MainMenu/helperComponents/MenuBottom/MenuBottom.d.ts +2 -0
  136. package/dist/esm/components/MainMenu/helperComponents/MenuDesktop/MenuDesktop.d.ts +1 -1
  137. package/dist/esm/components/MainMenu/helperComponents/MenuDesktop/MenuDesktop.js +7 -7
  138. package/dist/esm/components/MainMenu/helperComponents/MenuDesktop/styles.module.css +0 -6
  139. package/dist/esm/components/MainMenu/helperComponents/MenuHeaderBrand/MenuHeaderBrand.d.ts +3 -0
  140. package/dist/esm/components/MainMenu/helperComponents/MenuMobile/MenuMobile.d.ts +1 -1
  141. package/dist/esm/components/MainMenu/helperComponents/MenuMobile/MenuMobile.js +5 -6
  142. package/dist/esm/components/MainMenu/helperComponents/MenuMobile/styles.module.css +0 -7
  143. package/dist/esm/components/MainMenu/helperComponents/MountAnimation/MountAnimation.d.ts +1 -1
  144. package/dist/esm/components/MainMenu/helperComponents/MountAnimation/MountAnimation.js +4 -1
  145. package/dist/esm/components/MainMenu/helperComponents/ServiceCard/ServiceCard.d.ts +30 -6
  146. package/dist/esm/components/MainMenu/helperComponents/ServiceCard/ServiceCard.js +30 -20
  147. package/dist/esm/components/MainMenu/helperComponents/ServiceCard/styles.module.css +6 -1
  148. package/dist/esm/components/MainMenu/hooks/useMainMenuDnd.d.ts +6 -4
  149. package/dist/esm/components/MainMenu/hooks/useMainMenuDnd.js +6 -8
  150. package/dist/esm/components/MainMenu/hooks/useMenuItems.js +13 -8
  151. package/dist/esm/components/MainMenu/types.d.ts +31 -1
  152. package/dist/esm/components/MainMenu/utils/filterLinksGroupsFuzzy.d.ts +5 -0
  153. package/dist/esm/components/MainMenu/utils/filterLinksGroupsFuzzy.js +20 -7
  154. package/dist/esm/components/MainMenu/utils/flatLinksGroups.d.ts +2 -0
  155. package/dist/esm/components/MainMenu/utils/flatLinksGroups.js +4 -0
  156. package/dist/esm/components/MainMenu/utils/resolveInnerLinksByIds.d.ts +2 -2
  157. package/dist/esm/components/MainMenu/utils/resolveInnerLinksByIds.js +2 -4
  158. package/dist/esm/components/PathBreadcrumbs/PathBreadcrumbs.d.ts +1 -0
  159. package/dist/esm/components/UserMenu/UserMenu.d.ts +12 -0
  160. package/dist/esm/components/UserMenu/UserMenu.js +1 -1
  161. package/dist/esm/components/UserMenu/types.d.ts +7 -0
  162. package/dist/esm/style.css +48 -17
  163. package/dist/esm/utils/noop.d.ts +1 -0
  164. package/dist/esm/utils/noop.js +1 -0
  165. package/dist/tsconfig.cjs.tsbuildinfo +1 -1
  166. package/dist/tsconfig.esm.tsbuildinfo +1 -1
  167. package/package.json +28 -28
  168. package/src/components/HeaderButton/HeaderButton.tsx +2 -7
  169. package/src/components/HeaderLayout/HeaderLayout.tsx +6 -0
  170. package/src/components/Logo/Logo.tsx +7 -0
  171. package/src/components/MainMenu/MainMenu.tsx +11 -6
  172. package/src/components/MainMenu/helperComponents/Banners/MenuBanner.tsx +1 -1
  173. package/src/components/MainMenu/helperComponents/Content/Content.tsx +104 -59
  174. package/src/components/MainMenu/helperComponents/Content/cardsContext.ts +36 -0
  175. package/src/components/MainMenu/helperComponents/Content/helperComponents/ContentToolbar/ContentToolbar.tsx +9 -0
  176. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/SortableGroup.tsx +106 -47
  177. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupCards.tsx +18 -25
  178. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupDragHandle.tsx +2 -0
  179. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupHeader.tsx +11 -6
  180. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SortableGroupSkeleton.tsx +1 -0
  181. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategory.tsx +73 -97
  182. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/components/SubCategory/SubCategoryTitle.tsx +65 -49
  183. package/src/components/MainMenu/helperComponents/Content/helperComponents/SortableGroup/styles.module.scss +27 -0
  184. package/src/components/MainMenu/helperComponents/Content/hooks/useContentSegmentsSortable.ts +4 -2
  185. package/src/components/MainMenu/helperComponents/Content/hooks/useProgressiveCount.ts +46 -0
  186. package/src/components/MainMenu/helperComponents/Content/hooks/useSegmentDnd.tsx +8 -7
  187. package/src/components/MainMenu/helperComponents/Content/styles.module.scss +19 -0
  188. package/src/components/MainMenu/helperComponents/Favorites/Favorites.tsx +32 -84
  189. package/src/components/MainMenu/helperComponents/Favorites/components/Content.tsx +101 -0
  190. package/src/components/MainMenu/helperComponents/Favorites/components/EmptyState/EmptyState.tsx +6 -1
  191. package/src/components/MainMenu/helperComponents/Favorites/components/FavoritesList.tsx +59 -0
  192. package/src/components/MainMenu/helperComponents/Favorites/components/FavoritesReorderList.tsx +75 -0
  193. package/src/components/MainMenu/helperComponents/Favorites/components/RecentList.tsx +63 -0
  194. package/src/components/MainMenu/helperComponents/Favorites/components/SortableFavoriteCard.tsx +11 -4
  195. package/src/components/MainMenu/helperComponents/Favorites/components/index.ts +1 -1
  196. package/src/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesAutoSwitch.ts +32 -0
  197. package/src/components/MainMenu/helperComponents/Favorites/hooks/{useFavoritesDnd.tsx → useFavoritesReorder.tsx} +32 -30
  198. package/src/components/MainMenu/helperComponents/Favorites/styles.module.scss +16 -2
  199. package/src/components/MainMenu/helperComponents/Favorites/utils.ts +2 -2
  200. package/src/components/MainMenu/helperComponents/MenuBottom/MenuBottom.tsx +2 -0
  201. package/src/components/MainMenu/helperComponents/MenuDesktop/MenuDesktop.tsx +17 -11
  202. package/src/components/MainMenu/helperComponents/MenuDesktop/styles.module.scss +0 -7
  203. package/src/components/MainMenu/helperComponents/MenuHeaderBrand/MenuHeaderBrand.tsx +3 -0
  204. package/src/components/MainMenu/helperComponents/MenuMobile/MenuMobile.tsx +7 -10
  205. package/src/components/MainMenu/helperComponents/MenuMobile/styles.module.scss +0 -7
  206. package/src/components/MainMenu/helperComponents/MountAnimation/MountAnimation.tsx +5 -1
  207. package/src/components/MainMenu/helperComponents/ServiceCard/ServiceCard.tsx +91 -41
  208. package/src/components/MainMenu/helperComponents/ServiceCard/styles.module.scss +7 -1
  209. package/src/components/MainMenu/hooks/useMainMenuDnd.tsx +9 -12
  210. package/src/components/MainMenu/hooks/useMenuItems.tsx +34 -10
  211. package/src/components/MainMenu/types.ts +31 -1
  212. package/src/components/MainMenu/utils/filterLinksGroupsFuzzy.ts +29 -8
  213. package/src/components/MainMenu/utils/flatLinksGroups.ts +5 -0
  214. package/src/components/MainMenu/utils/resolveInnerLinksByIds.ts +3 -6
  215. package/src/components/PathBreadcrumbs/PathBreadcrumbs.tsx +1 -0
  216. package/src/components/UserMenu/UserMenu.tsx +17 -1
  217. package/src/components/UserMenu/types.ts +7 -0
  218. package/src/utils/noop.ts +1 -0
  219. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/FavoritesSortable.d.ts +0 -19
  220. package/dist/cjs/components/MainMenu/helperComponents/Favorites/components/FavoritesSortable.js +0 -30
  221. package/dist/cjs/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesDnd.d.ts +0 -25
  222. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/FavoritesSortable.d.ts +0 -19
  223. package/dist/esm/components/MainMenu/helperComponents/Favorites/components/FavoritesSortable.js +0 -24
  224. package/dist/esm/components/MainMenu/helperComponents/Favorites/hooks/useFavoritesDnd.d.ts +0 -25
  225. package/src/components/MainMenu/helperComponents/Favorites/components/FavoritesSortable.tsx +0 -78
@@ -14,12 +14,16 @@ const classnames_1 = __importDefault(require("classnames"));
14
14
  const react_1 = require("react");
15
15
  const locale_1 = require("../../../../locale");
16
16
  const emptyArray_1 = require("../../../../utils/emptyArray");
17
+ const noop_1 = require("../../../../utils/noop");
17
18
  const shouldBeOpenedInNewTab_1 = require("../../../../utils/shouldBeOpenedInNewTab");
18
19
  const utils_2 = require("../../utils");
20
+ const MountAnimation_1 = require("../MountAnimation");
21
+ const cardsContext_1 = require("./cardsContext");
19
22
  const constants_1 = require("./constants");
20
23
  const ContentToolbar_1 = require("./helperComponents/ContentToolbar");
21
24
  const SortableGroup_1 = require("./helperComponents/SortableGroup");
22
25
  const useContentSegmentsSortable_1 = require("./hooks/useContentSegmentsSortable");
26
+ const useProgressiveCount_1 = require("./hooks/useProgressiveCount");
23
27
  const useSegmentDnd_1 = require("./hooks/useSegmentDnd");
24
28
  const styles_module_scss_1 = __importDefault(require('./styles.module.css'));
25
29
  function Content({ searchValue, search, rightTop, segments, searchGroups = emptyArray_1.EMPTY_ARRAY, segmentPrefs, activeSegmentId, onActiveSegmentChange, onSegmentOrderChange, onSegmentExpandedChange, onSegmentServiceClick, className, footer, favorite, isMobile, preferences, loading, }) {
@@ -34,7 +38,8 @@ function Content({ searchValue, search, rightTop, segments, searchGroups = empty
34
38
  });
35
39
  const isSearching = Boolean(searchValue);
36
40
  const enableServiceDrag = Boolean(favorite) && !isMobile && !isSearching;
37
- const handleLinkClick = (0, react_1.useCallback)((service, e) => {
41
+ // Ссылки на обработчики стабильны: иначе `memo` карточек ломается при каждом рендере потребителя.
42
+ const handleLinkClick = (0, utils_1.useEventHandler)((service, e) => {
38
43
  if (service.disabled) {
39
44
  e?.preventDefault();
40
45
  return;
@@ -44,7 +49,11 @@ function Content({ searchValue, search, rightTop, segments, searchGroups = empty
44
49
  }
45
50
  onSegmentServiceClick?.(service, e);
46
51
  service.onClick?.(e);
47
- }, [onSegmentServiceClick]);
52
+ });
53
+ const handleFavoriteChange = (0, utils_1.useEventHandler)((productId) => (favorite ? favorite.onChange(productId) : noop_1.noop));
54
+ const favoriteValue = favorite?.value;
55
+ const favoriteIds = (0, react_1.useMemo)(() => (favoriteValue ? new Set(favoriteValue) : undefined), [favoriteValue]);
56
+ const showGroupsColors = preferences?.showGroupsColors?.value;
48
57
  const { orderedGroups, expandedIds, onExpandedChange, handleDragEnd: handleSortableDragEnd, } = (0, useContentSegmentsSortable_1.useContentSegmentsSortable)({
49
58
  segments,
50
59
  activeSegmentId: segmentId,
@@ -62,35 +71,50 @@ function Content({ searchValue, search, rightTop, segments, searchGroups = empty
62
71
  expandedIds,
63
72
  onSortableDragEnd: handleSortableDragEnd,
64
73
  showDescription,
65
- showGroupsColors: preferences?.showGroupsColors?.value,
66
- favorite,
74
+ showGroupsColors,
75
+ favoriteIds,
76
+ onFavoriteChange: handleFavoriteChange,
67
77
  });
68
- const allGroupsExpanded = visibleGroups.length > 0 && visibleGroups.every(({ id }) => expandedIds.includes(id));
78
+ // Первый экран монтируется сразу, остальные группы дорисовываются порциями (см. `useProgressiveCount`).
79
+ const renderedGroupsCount = (0, useProgressiveCount_1.useProgressiveCount)(visibleGroups.length, `${segmentId}|${isSearching}`, !loading);
80
+ const renderedGroups = (0, react_1.useMemo)(() => (renderedGroupsCount < visibleGroups.length ? visibleGroups.slice(0, renderedGroupsCount) : visibleGroups), [visibleGroups, renderedGroupsCount]);
81
+ const expandedIdsSet = (0, react_1.useMemo)(() => new Set(expandedIds), [expandedIds]);
82
+ const visibleGroupIds = (0, react_1.useMemo)(() => visibleGroups.map(({ id }) => id), [visibleGroups]);
83
+ const allGroupsExpanded = visibleGroups.length > 0 && visibleGroupIds.every(id => expandedIdsSet.has(id));
69
84
  const handleToggleAllGroupsExpanded = (0, react_1.useCallback)(() => {
70
- const visibleIds = visibleGroups.map(({ id }) => id);
71
85
  if (allGroupsExpanded) {
72
- onExpandedChange(expandedIds.filter(id => !visibleIds.includes(id)));
86
+ const visibleIdsSet = new Set(visibleGroupIds);
87
+ onExpandedChange(expandedIds.filter(id => !visibleIdsSet.has(id)));
73
88
  return;
74
89
  }
75
- onExpandedChange([...new Set([...expandedIds, ...visibleIds])]);
76
- }, [allGroupsExpanded, expandedIds, onExpandedChange, visibleGroups]);
90
+ onExpandedChange([...new Set([...expandedIds, ...visibleGroupIds])]);
91
+ }, [allGroupsExpanded, expandedIds, onExpandedChange, visibleGroupIds]);
92
+ const cardsContext = (0, react_1.useMemo)(() => ({
93
+ showDescription,
94
+ isMobile,
95
+ dragEnabled: enableServiceDrag,
96
+ favoriteIds,
97
+ onFavoriteChange: favoriteIds ? handleFavoriteChange : undefined,
98
+ onServiceClick: handleLinkClick,
99
+ }), [showDescription, isMobile, enableServiceDrag, favoriteIds, handleFavoriteChange, handleLinkClick]);
77
100
  const segmentItems = (0, react_1.useMemo)(() => segments?.map(segment => ({
78
101
  value: segment.id,
79
102
  label: segment.label,
80
103
  icon: segment.icon,
81
104
  })), [segments]);
82
105
  const hasCards = visibleGroups.length > 0;
106
+ const mountAnimationType = isMobile ? undefined : 'fade-slide-up-right';
83
107
  const cards = (() => {
84
108
  if (loading) {
85
109
  return Array.from({ length: 5 }).map((_, index) => (0, jsx_runtime_1.jsx)(SortableGroup_1.SortableGroupSkeleton, { isMobile: isMobile }, index));
86
110
  }
87
111
  if (hasCards) {
88
- return ((0, jsx_runtime_1.jsx)(sortable_1.SortableContext, { items: visibleGroups.map(({ id }) => id), strategy: sortable_1.verticalListSortingStrategy, children: (0, jsx_runtime_1.jsx)(accordion_1.Accordion, { selectionMode: 'multiple', expanded: expandedIds, onExpandedChange: onExpandedChange, children: visibleGroups.map(({ id, label, icon, items, favoritesEnabled, blockColor, highlight }) => ((0, jsx_runtime_1.jsx)(SortableGroup_1.SortableGroup, { id: id, icon: icon, label: label, items: items, isExpanded: expandedIds.includes(id), blockColor: (0, utils_2.resolveGroupBlockColor)(blockColor, preferences?.showGroupsColors?.value), showDescription: showDescription, isMobile: isMobile, enableServiceDrag: enableServiceDrag, favorite: favorite, groupFavoritesEnabled: favoritesEnabled, onServiceClick: handleLinkClick, highlight: highlight }, id))) }) }));
112
+ return ((0, jsx_runtime_1.jsx)(sortable_1.SortableContext, { items: visibleGroupIds, strategy: sortable_1.verticalListSortingStrategy, children: (0, jsx_runtime_1.jsx)(cardsContext_1.CardsContext.Provider, { value: cardsContext, children: (0, jsx_runtime_1.jsx)(accordion_1.Accordion, { selectionMode: 'multiple', expanded: expandedIds, onExpandedChange: onExpandedChange, children: renderedGroups.map(({ id, label, icon, items, favoritesEnabled, blockColor, highlight }) => ((0, jsx_runtime_1.jsx)(SortableGroup_1.SortableGroup, { id: id, icon: icon, label: label, items: items, isExpanded: expandedIdsSet.has(id), blockColor: (0, utils_2.resolveGroupBlockColor)(blockColor, showGroupsColors), isMobile: isMobile, enableServiceDrag: enableServiceDrag, groupFavoritesEnabled: favoritesEnabled, appear: !isMobile, highlight: highlight }, id))) }) }) }));
89
113
  }
90
114
  return ((0, jsx_runtime_1.jsx)(info_block_1.InfoBlock, { size: 'm', icon: {
91
115
  icon: isSearching ? system_1.SearchSVG : system_1.CrossSVG,
92
116
  appearance: 'neutral',
93
117
  }, content: isSearching ? t('noDataFound') : t('noData'), "data-test-id": isSearching ? constants_1.TEST_IDS.noDataFound : constants_1.TEST_IDS.noData, "data-mobile": isMobile || undefined, className: styles_module_scss_1.default.noData }));
94
118
  })();
95
- return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [search, (0, jsx_runtime_1.jsxs)("div", { className: (0, classnames_1.default)(styles_module_scss_1.default.content, className), "data-empty": (!loading && !hasCards) || undefined, children: [!isSearching && ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)(ContentToolbar_1.ContentToolbar, { segment: segmentId, onSegmentChange: setSegmentId, segmentItems: segmentItems, allGroupsExpanded: allGroupsExpanded, onToggleAllGroupsExpanded: handleToggleAllGroupsExpanded, preferences: preferences, isMobile: isMobile, loading: loading }), rightTop] })), cards, footer] })] }));
119
+ return ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [search, (0, jsx_runtime_1.jsxs)("div", { className: (0, classnames_1.default)(styles_module_scss_1.default.content, className), "data-mobile": isMobile || undefined, "data-empty": (!loading && !hasCards) || undefined, children: [!isSearching && ((0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, { children: (0, jsx_runtime_1.jsxs)(MountAnimation_1.MountAnimation, { type: mountAnimationType, className: styles_module_scss_1.default.top, children: [(0, jsx_runtime_1.jsx)(ContentToolbar_1.ContentToolbar, { segment: segmentId, onSegmentChange: setSegmentId, segmentItems: segmentItems, allGroupsExpanded: allGroupsExpanded, onToggleAllGroupsExpanded: handleToggleAllGroupsExpanded, preferences: preferences, isMobile: isMobile, loading: loading }), rightTop] }) })), cards, footer] })] }));
96
120
  }
@@ -0,0 +1,20 @@
1
+ import { MouseEvent } from 'react';
2
+ import { FavoriteProps, InnerLink } from '../../types';
3
+ export type CardsContextValue = {
4
+ showDescription: boolean;
5
+ isMobile?: boolean;
6
+ /** Карточки можно перетаскивать в избранное (иначе рендерятся без dnd-обвязки). */
7
+ dragEnabled: boolean;
8
+ /** Id избранных сервисов. Не передано — избранное для карточек недоступно. */
9
+ favoriteIds?: ReadonlySet<string>;
10
+ /** Стабильная по ссылке обёртка над `favorite.onChange`. */
11
+ onFavoriteChange?: FavoriteProps['onChange'];
12
+ /** Стабильная по ссылке обёртка над обработчиком клика по карточке. */
13
+ onServiceClick?(service: InnerLink, event?: MouseEvent<HTMLElement>): void;
14
+ };
15
+ /**
16
+ * Общие настройки карточек сервисов внутри группы. Заменяет сквозную передачу
17
+ * `showDescription` / `isMobile` / `favorite` / `onServiceClick` через все уровни сетки.
18
+ */
19
+ export declare const CardsContext: import("react").Context<CardsContextValue>;
20
+ export declare function useCardsContext(): CardsContextValue;
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.CardsContext = void 0;
4
+ exports.useCardsContext = useCardsContext;
5
+ const react_1 = require("react");
6
+ const DEFAULT_VALUE = {
7
+ showDescription: false,
8
+ dragEnabled: false,
9
+ };
10
+ /**
11
+ * Общие настройки карточек сервисов внутри группы. Заменяет сквозную передачу
12
+ * `showDescription` / `isMobile` / `favorite` / `onServiceClick` через все уровни сетки.
13
+ */
14
+ exports.CardsContext = (0, react_1.createContext)(DEFAULT_VALUE);
15
+ function useCardsContext() {
16
+ return (0, react_1.useContext)(exports.CardsContext);
17
+ }
@@ -1,18 +1,27 @@
1
1
  import { ReactNode } from 'react';
2
2
  import { MainMenuPreferencesProps } from '../../../../types';
3
3
  export type ContentToolbarSegmentItem = {
4
+ /** Значение сегмента (id). */
4
5
  value: string;
6
+ /** Подпись сегмента. */
5
7
  label: string;
8
+ /** Иконка сегмента. */
6
9
  icon?: ReactNode;
7
10
  };
8
11
  export type ContentToolbarProps = {
12
+ /** Значение активного сегмента SegmentControl. */
9
13
  segment: string;
14
+ /** Колбэк смены активного сегмента. */
10
15
  onSegmentChange(segment: string): void;
16
+ /** Пункты SegmentControl. Без пунктов (или с одним) SegmentControl не отображается. */
11
17
  segmentItems?: ContentToolbarSegmentItem[];
18
+ /** Все группы сегмента раскрыты — определяет иконку кнопки свернуть/развернуть все. */
12
19
  allGroupsExpanded: boolean;
20
+ /** Колбэк клика по кнопке свернуть/развернуть все группы. */
13
21
  onToggleAllGroupsExpanded(): void;
14
22
  /** Настройки меню (модалка по кнопке). Не передано — кнопка настроек не отображается. */
15
23
  preferences?: MainMenuPreferencesProps;
24
+ /** Мобильная раскладка — кнопка свернуть/развернуть все скрывается. */
16
25
  isMobile?: boolean;
17
26
  /** Флаг загрузки данных — сегменты подгружаются с бэка, поэтому SegmentControl тоже уходит в скелетон. */
18
27
  loading?: boolean;
@@ -1,12 +1,31 @@
1
1
  import { LinksGroup, LinksGroupBlockColor, LinksGroupTitle } from '../../../../types';
2
- import { SortableGroupCardsProps } from './components';
3
- export type SortableGroupProps = Omit<SortableGroupCardsProps, 'groupId'> & Pick<LinksGroup, 'icon'> & {
2
+ import { CardsContextValue } from '../../cardsContext';
3
+ export type SortableGroupProps = Pick<LinksGroup, 'icon' | 'items'> & {
4
+ /** Id группы. */
4
5
  id: string;
6
+ /** Заголовок группы. */
5
7
  label: LinksGroupTitle;
8
+ /** Раскрыта ли группа. */
6
9
  isExpanded?: boolean;
10
+ /** Мобильная раскладка. */
11
+ isMobile?: boolean;
12
+ /** Группу можно перетаскивать (иначе рендерится без `useSortable`). */
13
+ enableServiceDrag?: boolean;
14
+ /** Цвет блока группы. */
7
15
  blockColor?: LinksGroupBlockColor;
16
+ /** Визуальное выделение группы. */
8
17
  highlight?: boolean;
18
+ /** Разрешено ли добавление карточек группы в избранное. */
9
19
  groupFavoritesEnabled?: boolean;
20
+ /** Группа появляется с fade-in при монтировании (на desktop; на mobile анимирует контейнер). */
21
+ appear?: boolean;
10
22
  };
11
- export declare function SortableGroup({ id, icon, label, items, isExpanded, showDescription, isMobile, enableServiceDrag, favorite, groupFavoritesEnabled, onServiceClick, blockColor, highlight, }: SortableGroupProps): import("react/jsx-runtime").JSX.Element;
12
- export declare function SortableGroupDragPreview({ id, label, items, isExpanded, showDescription, isMobile, favorite, groupFavoritesEnabled, blockColor, highlight, }: Omit<SortableGroupProps, 'enableServiceDrag'>): import("react/jsx-runtime").JSX.Element;
23
+ declare function SortableGroupBase(props: SortableGroupProps): import("react/jsx-runtime").JSX.Element;
24
+ export declare const SortableGroup: import("react").MemoExoticComponent<typeof SortableGroupBase>;
25
+ export type SortableGroupDragPreviewProps = Omit<SortableGroupProps, 'enableServiceDrag'> & Pick<CardsContextValue, 'showDescription' | 'favoriteIds' | 'onFavoriteChange'>;
26
+ /**
27
+ * Превью группы в `DragOverlay`. Рендерится вне `Content`, поэтому свой `CardsContext` собирает
28
+ * сам: без drag-обвязки карточек и без обработчика клика.
29
+ */
30
+ export declare function SortableGroupDragPreview({ id, label, items, isExpanded, showDescription, isMobile, favoriteIds, onFavoriteChange, groupFavoritesEnabled, blockColor, highlight, }: SortableGroupDragPreviewProps): import("react/jsx-runtime").JSX.Element;
31
+ export {};
@@ -3,7 +3,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.SortableGroup = SortableGroup;
6
+ exports.SortableGroup = void 0;
7
7
  exports.SortableGroupDragPreview = SortableGroupDragPreview;
8
8
  const jsx_runtime_1 = require("react/jsx-runtime");
9
9
  const sortable_1 = require("@dnd-kit/sortable");
@@ -11,14 +11,27 @@ const utilities_1 = require("@dnd-kit/utilities");
11
11
  const accordion_1 = require("@cloud-ru/ds-accordion");
12
12
  const drag_and_drop_1 = require("@cloud-ru/ds-drag-and-drop");
13
13
  const theme_1 = require("@cloud-ru/ds-theme");
14
+ const react_1 = require("react");
15
+ const cardsContext_1 = require("../../cardsContext");
14
16
  const constants_1 = require("../../constants");
15
17
  const components_1 = require("./components");
16
18
  const styles_module_scss_1 = __importDefault(require('./styles.module.css'));
17
- function SortableGroup({ id, icon, label, items, isExpanded, showDescription, isMobile, enableServiceDrag, favorite, groupFavoritesEnabled = true, onServiceClick, blockColor, highlight, }) {
18
- const { attributes, listeners, setNodeRef, transform, transition, isDragging } = (0, sortable_1.useSortable)({
19
- id,
20
- disabled: !enableServiceDrag,
21
- });
19
+ function GroupView({ id, icon, label, items, isExpanded, isMobile, enableServiceDrag, groupFavoritesEnabled = true, blockColor, highlight, appear, attributes, listeners, setNodeRef, style, isDragging, }) {
20
+ const { colorScheme } = (0, theme_1.useThemeAppearance)().appearance;
21
+ // Появление проигрывается один раз. React переставляет узлы `insertBefore`, а браузер при
22
+ // повторной вставке перезапускает CSS-анимацию — при перетаскивании группы соседи «моргали».
23
+ // После окончания флаг снимается, и перестановка анимацию уже не запускает.
24
+ const [isAppearing, setIsAppearing] = (0, react_1.useState)(Boolean(appear));
25
+ const handleAnimationEnd = (0, react_1.useCallback)((event) => {
26
+ // `animationend` всплывает от вложенных анимаций — нужна только своя.
27
+ if (event.target === event.currentTarget) {
28
+ setIsAppearing(false);
29
+ }
30
+ }, []);
31
+ return ((0, jsx_runtime_1.jsxs)(drag_and_drop_1.DragGhost, { innerRef: setNodeRef, id: id, style: style, className: styles_module_scss_1.default.group, dragging: isDragging, mode: drag_and_drop_1.DRAG_MODE.Dynamic, "data-appear": isAppearing || undefined, onAnimationEnd: handleAnimationEnd, "data-test-id": `${constants_1.TEST_IDS.groupCard}-${id}`, children: [(0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decoration, "data-color-scheme": colorScheme, "data-is-highlighted": highlight || undefined, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decorationBackground, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.colorMarker, "data-block-color": blockColor }) }) }), (0, jsx_runtime_1.jsx)(accordion_1.Accordion.CollapseBlockTertiary, { id: id, showChevron: false, afterTitle: (0, jsx_runtime_1.jsx)(components_1.SortableGroupHeader, { label: label, icon: icon, isExpanded: isExpanded, enableServiceDrag: enableServiceDrag, attributes: attributes, listeners: listeners, isMobile: isMobile }), children: (0, jsx_runtime_1.jsx)(components_1.SortableGroupCards, { groupId: id, items: items, groupFavoritesEnabled: groupFavoritesEnabled }) })] }));
32
+ }
33
+ function DraggableGroup(props) {
34
+ const { attributes, listeners, setNodeRef, transform, transition, isDragging } = (0, sortable_1.useSortable)({ id: props.id });
22
35
  const style = {
23
36
  // CSS.Transform добавляет scaleX/scaleY, из-за чего перетаскиваемая группа "растягивается"
24
37
  // при пересечении с соседней группой другой высоты. CSS.Translate использует только сдвиг.
@@ -27,10 +40,25 @@ function SortableGroup({ id, icon, label, items, isExpanded, showDescription, is
27
40
  transform: transform ? utilities_1.CSS.Translate.toString(transform) : undefined,
28
41
  transition,
29
42
  };
30
- const { colorScheme } = (0, theme_1.useThemeAppearance)().appearance;
31
- return ((0, jsx_runtime_1.jsxs)(drag_and_drop_1.DragGhost, { innerRef: setNodeRef, id: id, style: style, className: styles_module_scss_1.default.group, dragging: isDragging, mode: drag_and_drop_1.DRAG_MODE.Dynamic, "data-test-id": `${constants_1.TEST_IDS.groupCard}-${id}`, children: [(0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decoration, "data-color-scheme": colorScheme, "data-is-highlighted": highlight || undefined, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decorationBackground, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.colorMarker, "data-block-color": blockColor }) }) }), (0, jsx_runtime_1.jsx)(accordion_1.Accordion.CollapseBlockTertiary, { id: id, showChevron: false, afterTitle: (0, jsx_runtime_1.jsx)(components_1.SortableGroupHeader, { label: label, icon: icon, isExpanded: isExpanded, enableServiceDrag: enableServiceDrag, attributes: attributes, listeners: listeners, isMobile: isMobile }), children: (0, jsx_runtime_1.jsx)(components_1.SortableGroupCards, { groupId: id, items: items, showDescription: showDescription, isMobile: isMobile, enableServiceDrag: enableServiceDrag, favorite: favorite, groupFavoritesEnabled: groupFavoritesEnabled, onServiceClick: onServiceClick }) })] }));
43
+ return ((0, jsx_runtime_1.jsx)(GroupView, { ...props, attributes: attributes, listeners: listeners, setNodeRef: setNodeRef, style: style, isDragging: isDragging }));
32
44
  }
33
- function SortableGroupDragPreview({ id, label, items, isExpanded, showDescription, isMobile, favorite, groupFavoritesEnabled, blockColor, highlight, }) {
45
+ function SortableGroupBase(props) {
46
+ // Без drag (mobile, поиск, нет избранного) группа не регистрируется в `SortableContext`.
47
+ return props.enableServiceDrag ? (0, jsx_runtime_1.jsx)(DraggableGroup, { ...props }) : (0, jsx_runtime_1.jsx)(GroupView, { ...props });
48
+ }
49
+ exports.SortableGroup = (0, react_1.memo)(SortableGroupBase);
50
+ /**
51
+ * Превью группы в `DragOverlay`. Рендерится вне `Content`, поэтому свой `CardsContext` собирает
52
+ * сам: без drag-обвязки карточек и без обработчика клика.
53
+ */
54
+ function SortableGroupDragPreview({ id, label, items, isExpanded, showDescription, isMobile, favoriteIds, onFavoriteChange, groupFavoritesEnabled, blockColor, highlight, }) {
34
55
  const { colorScheme } = (0, theme_1.useThemeAppearance)().appearance;
35
- return ((0, jsx_runtime_1.jsx)(drag_and_drop_1.DragPreview, { className: styles_module_scss_1.default.groupDragPreview, children: (0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.group, "data-drag-preview": true, children: [(0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decoration, "data-color-scheme": colorScheme, "data-is-highlighted": highlight || undefined, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decorationBackground, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.colorMarker, "data-block-color": blockColor }) }) }), (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupDragPreviewHeader, children: (0, jsx_runtime_1.jsx)(components_1.SortableGroupHeader, { label: label, isExpanded: isExpanded, isMobile: isMobile, enableServiceDrag: true }) }), isExpanded && ((0, jsx_runtime_1.jsx)(components_1.SortableGroupCards, { groupId: id, items: items, showDescription: showDescription, isMobile: isMobile, favorite: favorite, groupFavoritesEnabled: groupFavoritesEnabled }))] }) }));
56
+ const cardsContext = {
57
+ showDescription,
58
+ isMobile,
59
+ dragEnabled: false,
60
+ favoriteIds,
61
+ onFavoriteChange,
62
+ };
63
+ return ((0, jsx_runtime_1.jsx)(drag_and_drop_1.DragPreview, { className: styles_module_scss_1.default.groupDragPreview, children: (0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.group, "data-drag-preview": true, children: [(0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decoration, "data-color-scheme": colorScheme, "data-is-highlighted": highlight || undefined, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.decorationBackground, children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.colorMarker, "data-block-color": blockColor }) }) }), (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupDragPreviewHeader, children: (0, jsx_runtime_1.jsx)(components_1.SortableGroupHeader, { label: label, isExpanded: isExpanded, isMobile: isMobile, enableServiceDrag: true }) }), isExpanded && ((0, jsx_runtime_1.jsx)(cardsContext_1.CardsContext.Provider, { value: cardsContext, children: (0, jsx_runtime_1.jsx)(components_1.SortableGroupCards, { groupId: id, items: items, groupFavoritesEnabled: groupFavoritesEnabled }) }))] }) }));
36
64
  }
@@ -1,9 +1,12 @@
1
1
  import { InnerLink } from '../../../../../types';
2
- import { ServiceCardProps } from '../../../../ServiceCard';
3
- export type SortableGroupCardsProps = Pick<ServiceCardProps, 'showDescription' | 'isMobile' | 'favorite' | 'onServiceClick'> & {
2
+ export type SortableGroupCardsProps = {
3
+ /** Id группы-предка. */
4
4
  groupId: string;
5
+ /** Карточки сервисов группы. */
5
6
  items: InnerLink[];
6
- enableServiceDrag?: boolean;
7
+ /** Разрешено ли добавление карточек группы в избранное. */
7
8
  groupFavoritesEnabled?: boolean;
8
9
  };
9
- export declare function SortableGroupCards({ groupId, items, showDescription, isMobile, enableServiceDrag, favorite, groupFavoritesEnabled, onServiceClick, }: SortableGroupCardsProps): import("react/jsx-runtime").JSX.Element;
10
+ declare function SortableGroupCardsBase({ groupId, items, groupFavoritesEnabled }: SortableGroupCardsProps): import("react/jsx-runtime").JSX.Element;
11
+ export declare const SortableGroupCards: import("react").MemoExoticComponent<typeof SortableGroupCardsBase>;
12
+ export {};
@@ -3,19 +3,23 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.SortableGroupCards = SortableGroupCards;
6
+ exports.SortableGroupCards = void 0;
7
7
  const jsx_runtime_1 = require("react/jsx-runtime");
8
8
  const react_1 = require("react");
9
9
  const ServiceCard_1 = require("../../../../ServiceCard");
10
+ const cardsContext_1 = require("../../../cardsContext");
10
11
  const styles_module_scss_1 = __importDefault(require('../styles.module.css'));
11
12
  const utils_1 = require("../utils");
12
13
  const SubCategory_1 = require("./SubCategory");
13
- function SortableGroupCards({ groupId, items, showDescription, isMobile, enableServiceDrag, favorite, groupFavoritesEnabled, onServiceClick, }) {
14
+ function SortableGroupCardsBase({ groupId, items, groupFavoritesEnabled }) {
15
+ const { isMobile, showDescription, dragEnabled, favoriteIds, onFavoriteChange, onServiceClick } = (0, cardsContext_1.useCardsContext)();
16
+ const cardFavoriteChange = favoriteIds ? onFavoriteChange : undefined;
14
17
  const blocks = (0, react_1.useMemo)(() => (0, utils_1.splitIntoBlocks)(items), [items]);
15
18
  return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupBlocks, children: blocks.map(block => {
16
19
  if (block.type === 'subcategory') {
17
- return ((0, jsx_runtime_1.jsx)(SubCategory_1.SubCategory, { groupId: groupId, service: block.service, showDescription: showDescription, isMobile: isMobile, dragDisabled: !enableServiceDrag, favorite: favorite, groupFavoritesEnabled: groupFavoritesEnabled, onServiceClick: onServiceClick }, String(groupId) + block.service.id));
20
+ return ((0, jsx_runtime_1.jsx)(SubCategory_1.SubCategory, { groupId: groupId, service: block.service, groupFavoritesEnabled: groupFavoritesEnabled }, String(groupId) + block.service.id));
18
21
  }
19
- return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupBody, "data-mobile": isMobile || undefined, "data-show-description": showDescription || undefined, children: block.services.map(service => ((0, jsx_runtime_1.jsx)(ServiceCard_1.DraggableServiceCard, { groupId: groupId, service: service, favorite: favorite, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescription, dragDisabled: !enableServiceDrag }, String(groupId) + service.id))) }, String(groupId) + block.services[0].id));
22
+ return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupBody, "data-mobile": isMobile || undefined, "data-show-description": showDescription || undefined, children: block.services.map(service => ((0, jsx_runtime_1.jsx)(ServiceCard_1.GridServiceCard, { groupId: groupId, service: service, favoriteChecked: favoriteIds?.has(service.id), onFavoriteChange: cardFavoriteChange, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescription, dragEnabled: dragEnabled }, String(groupId) + service.id))) }, String(groupId) + block.services[0].id));
20
23
  }) }));
21
24
  }
25
+ exports.SortableGroupCards = (0, react_1.memo)(SortableGroupCardsBase);
@@ -1,6 +1,8 @@
1
1
  import { DraggableAttributes, DraggableSyntheticListeners } from '@dnd-kit/core';
2
2
  export type SortableGroupDragHandleProps = {
3
+ /** ARIA-атрибуты `dnd-kit` draggable-элемента. */
3
4
  attributes?: DraggableAttributes;
5
+ /** Обработчики событий `dnd-kit` для инициации перетаскивания. */
4
6
  listeners?: DraggableSyntheticListeners;
5
7
  };
6
8
  export declare function SortableGroupDragHandle({ attributes, listeners }: SortableGroupDragHandleProps): import("react/jsx-runtime").JSX.Element;
@@ -6,4 +6,6 @@ export type SortableGroupHeaderProps = Pick<LinksGroup, 'icon'> & {
6
6
  enableServiceDrag?: boolean;
7
7
  isMobile?: boolean;
8
8
  } & SortableGroupDragHandleProps;
9
- export declare function SortableGroupHeader({ label, icon, isExpanded, enableServiceDrag, attributes, listeners, isMobile, }: SortableGroupHeaderProps): import("react/jsx-runtime").JSX.Element;
9
+ declare function SortableGroupHeaderBase({ label, icon, isExpanded, enableServiceDrag, attributes, listeners, isMobile, }: SortableGroupHeaderProps): import("react/jsx-runtime").JSX.Element;
10
+ export declare const SortableGroupHeader: import("react").MemoExoticComponent<typeof SortableGroupHeaderBase>;
11
+ export {};
@@ -3,19 +3,21 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.SortableGroupHeader = SortableGroupHeader;
6
+ exports.SortableGroupHeader = void 0;
7
7
  const jsx_runtime_1 = require("react/jsx-runtime");
8
8
  const button_1 = require("@cloud-ru/ds-button");
9
9
  const system_1 = require("@cloud-ru/ds-icons/interface/system");
10
10
  const typography_1 = require("@cloud-ru/ds-typography");
11
11
  const uikit_product_title_clickable_1 = require("@cloud-ru/ds-uikit-product-title-clickable");
12
+ const react_1 = require("react");
12
13
  const utils_1 = require("../../../../../utils");
13
14
  const styles_module_scss_1 = __importDefault(require('../styles.module.css'));
14
15
  const SortableGroupDragHandle_1 = require("./SortableGroupDragHandle");
15
- function SortableGroupHeader({ label, icon, isExpanded, enableServiceDrag, attributes, listeners, isMobile, }) {
16
- const handleLabelClick = e => {
16
+ function SortableGroupHeaderBase({ label, icon, isExpanded, enableServiceDrag, attributes, listeners, isMobile, }) {
17
+ const handleLabelClick = (0, react_1.useCallback)(e => {
17
18
  e.stopPropagation();
18
19
  label?.onClick?.(e);
19
- };
20
+ }, [label]);
20
21
  return ((0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.header, "data-expanded": isExpanded || undefined, children: [(0, jsx_runtime_1.jsx)(typography_1.Typography, { variant: 'title', size: 'm', className: styles_module_scss_1.default.headerTitle, "data-test-id": 'header__drawer-menu__group-card-title', children: label.onClick || label.href ? ((0, jsx_runtime_1.jsx)(uikit_product_title_clickable_1.TitleClickable, { ...(label.href ? { as: 'a', href: label.href } : { as: 'div' }), onClick: handleLabelClick, title: label.text, icon: (0, utils_1.getLinkEmblem)({ icon }) })) : (label.text) }), (enableServiceDrag || !isMobile) && ((0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.headerActions, "data-always-visible": isMobile || undefined, children: [enableServiceDrag && (0, jsx_runtime_1.jsx)(SortableGroupDragHandle_1.SortableGroupDragHandle, { attributes: attributes, listeners: listeners }), !isMobile && ((0, jsx_runtime_1.jsx)(button_1.Button, { view: 'elevated', appearance: 'neutral', size: 's', icon: isExpanded ? (0, jsx_runtime_1.jsx)(system_1.ChevronUpSVG, {}) : (0, jsx_runtime_1.jsx)(system_1.ChevronDownSVG, {}), "data-test-id": 'header__drawer-menu__group-card-collapse' }))] }))] }));
21
22
  }
23
+ exports.SortableGroupHeader = (0, react_1.memo)(SortableGroupHeaderBase);
@@ -1,4 +1,5 @@
1
1
  type SortableGroupSkeletonProps = {
2
+ /** Мобильная раскладка. */
2
3
  isMobile?: boolean;
3
4
  };
4
5
  export declare function SortableGroupSkeleton({ isMobile }: SortableGroupSkeletonProps): import("react/jsx-runtime").JSX.Element;
@@ -1,7 +1,12 @@
1
- import { ServiceCardProps } from '../../../../../ServiceCard';
2
- export type SubCategoryProps = Pick<ServiceCardProps, 'service' | 'onServiceClick' | 'favorite' | 'showDescription' | 'isMobile'> & {
1
+ import { InnerLink } from '../../../../../../types';
2
+ export type SubCategoryProps = {
3
+ /** Id группы-предка. */
3
4
  groupId: string;
4
- dragDisabled?: boolean;
5
+ /** Карточка подкатегории (с непустым {@link InnerLink.items}). */
6
+ service: InnerLink;
7
+ /** Разрешено ли добавление карточек группы в избранное. */
5
8
  groupFavoritesEnabled?: boolean;
6
9
  };
7
- export declare function SubCategory({ groupId, service, showDescription, isMobile, dragDisabled, favorite, onServiceClick, groupFavoritesEnabled, }: SubCategoryProps): import("react/jsx-runtime").JSX.Element;
10
+ declare function SubCategoryBase({ groupId, service, groupFavoritesEnabled }: SubCategoryProps): import("react/jsx-runtime").JSX.Element;
11
+ export declare const SubCategory: import("react").MemoExoticComponent<typeof SubCategoryBase>;
12
+ export {};
@@ -3,18 +3,25 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.SubCategory = SubCategory;
6
+ exports.SubCategory = void 0;
7
7
  const jsx_runtime_1 = require("react/jsx-runtime");
8
8
  const accordion_1 = require("@cloud-ru/ds-accordion");
9
9
  const react_1 = require("react");
10
+ const noop_1 = require("../../../../../../../../utils/noop");
10
11
  const innerLink_1 = require("../../../../../../utils/innerLink");
11
12
  const ServiceCard_1 = require("../../../../../ServiceCard");
13
+ const cardsContext_1 = require("../../../../cardsContext");
12
14
  const constants_1 = require("../../../../constants");
13
15
  const styles_module_scss_1 = __importDefault(require('../../styles.module.css'));
14
16
  const styles_module_scss_2 = __importDefault(require('./styles.module.css'));
15
17
  const SubCategoryTitle_1 = require("./SubCategoryTitle");
16
- const noop = () => { };
17
- function SubCategory({ groupId, service, showDescription, isMobile, dragDisabled, favorite, onServiceClick, groupFavoritesEnabled, }) {
18
+ const TITLE_ONLY_EXPANDABLE = { value: true, onClick: noop_1.noop };
19
+ const SubCategoryBody = (0, react_1.memo)(function SubCategoryBody({ nestedGroupId, items, variant }) {
20
+ const { isMobile, showDescription, dragEnabled, favoriteIds, onFavoriteChange, onServiceClick } = (0, cardsContext_1.useCardsContext)();
21
+ const cardFavoriteChange = favoriteIds ? onFavoriteChange : undefined;
22
+ return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupBody, "data-subcategory-body": variant === 'expanded' ? 'expanded' : true, "data-mobile": isMobile || undefined, "data-show-description": showDescription || undefined, children: items.map(nestedService => ((0, jsx_runtime_1.jsx)(ServiceCard_1.GridServiceCard, { groupId: nestedGroupId, service: nestedService, favoriteChecked: favoriteIds?.has(nestedService.id), onFavoriteChange: cardFavoriteChange, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescription, dragEnabled: dragEnabled }, nestedGroupId + nestedService.id))) }));
23
+ });
24
+ function SubCategoryBase({ groupId, service, groupFavoritesEnabled }) {
18
25
  const subcategoryId = (0, innerLink_1.getSubCategoryId)(groupId, service.id);
19
26
  const nestedGroupId = (0, innerLink_1.getNestedServiceGroupId)(groupId, service.id);
20
27
  const nestedItems = (0, react_1.useMemo)(() => service.items?.filter(item => !item.hidden) ?? [], [service.items]);
@@ -28,19 +35,17 @@ function SubCategory({ groupId, service, showDescription, isMobile, dragDisabled
28
35
  setIsExpanded(isExpanded ? undefined : subcategoryId);
29
36
  }
30
37
  }, [isExpanded, subcategoryId, isExpandableEnabled]);
38
+ const expandable = (0, react_1.useMemo)(() => ({ value: Boolean(isExpanded), onClick: handleExpandedChange }), [isExpanded, handleExpandedChange]);
39
+ const testId = `${constants_1.TEST_IDS.subcategory}-${service.id}`;
40
+ const title = ((0, jsx_runtime_1.jsx)(SubCategoryTitle_1.SubCategoryTitle, { groupId: groupId, service: service, expandable: viewMode === 'group-title-only' ? TITLE_ONLY_EXPANDABLE : expandable, groupFavoritesEnabled: groupFavoritesEnabled }));
31
41
  // 'group-title-only' — только заголовок подкатегории, без раскрываемого тела и кнопки
32
42
  // переключения: карточка ведёт себя как обычная ссылка (см. isSubCategoryCard в utils/innerLink).
33
43
  if (viewMode === 'group-title-only') {
34
- return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_2.default.subcategory, "data-title-only": true, "data-test-id": `${constants_1.TEST_IDS.subcategory}-${service.id}`, children: (0, jsx_runtime_1.jsx)(SubCategoryTitle_1.SubCategoryTitle, { groupId: groupId, service: service, expandable: { value: true, onClick: noop }, showDescription: showDescription, isMobile: isMobile, dragDisabled: dragDisabled, favorite: groupFavoritesEnabled ? favorite : undefined, onServiceClick: onServiceClick }) }));
44
+ return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_2.default.subcategory, "data-title-only": true, "data-test-id": testId, children: title }));
35
45
  }
36
46
  if (viewMode === 'expanded') {
37
- return ((0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_2.default.subcategory, "data-test-id": `${constants_1.TEST_IDS.subcategory}-${service.id}`, children: [(0, jsx_runtime_1.jsx)(SubCategoryTitle_1.SubCategoryTitle, { groupId: groupId, service: service, expandable: {
38
- value: Boolean(isExpanded),
39
- onClick: handleExpandedChange,
40
- }, showDescription: showDescription, isMobile: isMobile, dragDisabled: dragDisabled, favorite: groupFavoritesEnabled ? favorite : undefined, onServiceClick: onServiceClick }), (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupBody, "data-subcategory-body": 'expanded', "data-mobile": isMobile || undefined, "data-show-description": showDescription || undefined, children: nestedItems.map(nestedService => ((0, jsx_runtime_1.jsx)(ServiceCard_1.DraggableServiceCard, { groupId: nestedGroupId, service: nestedService, favorite: favorite, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescription, dragDisabled: dragDisabled }, nestedGroupId + nestedService.id))) })] }));
47
+ return ((0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_2.default.subcategory, "data-test-id": testId, children: [title, (0, jsx_runtime_1.jsx)(SubCategoryBody, { nestedGroupId: nestedGroupId, items: nestedItems, variant: 'expanded' })] }));
41
48
  }
42
- return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_2.default.subcategory, "data-test-id": `${constants_1.TEST_IDS.subcategory}-${service.id}`, children: (0, jsx_runtime_1.jsx)(accordion_1.Accordion, { selectionMode: 'single', expanded: isExpanded, onExpandedChange: handleExpandedChange, children: (0, jsx_runtime_1.jsx)(accordion_1.Accordion.CollapseBlockTertiary, { id: subcategoryId, showChevron: false, className: styles_module_scss_2.default.subcategoryAccordion, afterTitle: (0, jsx_runtime_1.jsx)(SubCategoryTitle_1.SubCategoryTitle, { groupId: groupId, service: service, expandable: {
43
- value: Boolean(isExpanded),
44
- onClick: handleExpandedChange,
45
- }, showDescription: showDescription, isMobile: isMobile, dragDisabled: dragDisabled, favorite: groupFavoritesEnabled ? favorite : undefined, onServiceClick: onServiceClick }), children: (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.groupBody, "data-subcategory-body": true, "data-mobile": isMobile || undefined, "data-show-description": showDescription || undefined, children: nestedItems.map(nestedService => ((0, jsx_runtime_1.jsx)(ServiceCard_1.DraggableServiceCard, { groupId: nestedGroupId, service: nestedService, favorite: favorite, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescription, dragDisabled: dragDisabled }, nestedGroupId + nestedService.id))) }) }) }) }));
49
+ return ((0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_2.default.subcategory, "data-test-id": testId, children: (0, jsx_runtime_1.jsx)(accordion_1.Accordion, { selectionMode: 'single', expanded: isExpanded, onExpandedChange: handleExpandedChange, children: (0, jsx_runtime_1.jsx)(accordion_1.Accordion.CollapseBlockTertiary, { id: subcategoryId, showChevron: false, className: styles_module_scss_2.default.subcategoryAccordion, afterTitle: title, children: (0, jsx_runtime_1.jsx)(SubCategoryBody, { nestedGroupId: nestedGroupId, items: nestedItems, variant: 'expandable' }) }) }) }));
46
50
  }
51
+ exports.SubCategory = (0, react_1.memo)(SubCategoryBase);
@@ -1,5 +1,10 @@
1
- import { DraggableServiceCardProps } from '../../../../../ServiceCard';
1
+ import { GridServiceCardProps } from '../../../../../ServiceCard';
2
2
  export type SubCategoryTitleProps = {
3
+ /** Id группы-предка. */
3
4
  groupId: string;
4
- } & Pick<DraggableServiceCardProps, 'expandable' | 'service' | 'onServiceClick' | 'favorite' | 'showDescription' | 'isMobile' | 'dragDisabled'>;
5
- export declare function SubCategoryTitle({ groupId, service, showDescription: showDescriptionProp, isMobile, dragDisabled, favorite, onServiceClick, expandable, }: SubCategoryTitleProps): import("react/jsx-runtime").JSX.Element;
5
+ /** Кнопка избранного показывается только если для группы избранное включено. */
6
+ groupFavoritesEnabled?: boolean;
7
+ } & Pick<GridServiceCardProps, 'expandable' | 'service'>;
8
+ declare function SubCategoryTitleBase({ groupId, service, groupFavoritesEnabled, expandable }: SubCategoryTitleProps): import("react/jsx-runtime").JSX.Element;
9
+ export declare const SubCategoryTitle: import("react").MemoExoticComponent<typeof SubCategoryTitleBase>;
10
+ export {};
@@ -3,7 +3,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.SubCategoryTitle = SubCategoryTitle;
6
+ exports.SubCategoryTitle = void 0;
7
7
  const jsx_runtime_1 = require("react/jsx-runtime");
8
8
  const typography_1 = require("@cloud-ru/ds-typography");
9
9
  const uikit_product_card_predefined_1 = require("@cloud-ru/ds-uikit-product-card-predefined");
@@ -12,53 +12,59 @@ const utils_1 = require("@cloud-ru/ds-utils");
12
12
  const react_1 = require("react");
13
13
  const utils_2 = require("../../../../../../utils");
14
14
  const ServiceCard_1 = require("../../../../../ServiceCard");
15
+ const cardsContext_1 = require("../../../../cardsContext");
15
16
  const constants_1 = require("../../../../constants");
16
17
  const styles_module_scss_1 = __importDefault(require('./styles.module.css'));
17
- function SubCategoryTitle({ groupId, service, showDescription: showDescriptionProp, isMobile, dragDisabled, favorite, onServiceClick, expandable, }) {
18
+ function SubCategoryTitleBase({ groupId, service, groupFavoritesEnabled, expandable }) {
19
+ const { isMobile, showDescription: showDescriptionProp, dragEnabled, favoriteIds, onFavoriteChange, onServiceClick, } = (0, cardsContext_1.useCardsContext)();
18
20
  const titleRef = (0, react_1.useRef)(null);
19
21
  const tooltipTriggerRef = (0, react_1.useRef)(null);
20
22
  const favoriteRef = (0, react_1.useRef)(null);
21
- const handleServiceClick = (event) => {
23
+ const { id, description, icon } = service;
24
+ const handleServiceClick = (0, react_1.useCallback)((event) => {
22
25
  (0, utils_1.stopEventPropagation)(event);
23
26
  onServiceClick?.(service, event);
24
- };
25
- const titleTestId = `${constants_1.TEST_IDS.subcategoryTitle}-${service.id}`;
26
- const isFavorite = Boolean(favorite?.value.includes(service.id));
27
- const showDescription = showDescriptionProp && Boolean(service.description);
28
- const hasTooltip = !showDescription && service.description;
29
- const handleKeyDown = (0, uikit_product_card_predefined_1.createCardActionsKeyDownHandler)({
27
+ }, [onServiceClick, service]);
28
+ const titleTestId = `${constants_1.TEST_IDS.subcategoryTitle}-${id}`;
29
+ const cardFavoriteChange = groupFavoritesEnabled && favoriteIds ? onFavoriteChange : undefined;
30
+ const isFavorite = Boolean(favoriteIds?.has(id));
31
+ const showDescription = showDescriptionProp && Boolean(description);
32
+ const hasTooltip = !showDescription && Boolean(description);
33
+ const handleKeyDown = (0, react_1.useMemo)(() => (0, uikit_product_card_predefined_1.createCardActionsKeyDownHandler)({
30
34
  cardRef: titleRef,
31
35
  items: [
32
36
  hasTooltip ? { ref: tooltipTriggerRef } : null,
33
- favorite
37
+ cardFavoriteChange
34
38
  ? {
35
39
  ref: favoriteRef,
36
- onActivate: () => favorite.onChange(service.id)(!isFavorite),
40
+ onActivate: () => cardFavoriteChange(id)(!isFavorite),
37
41
  }
38
42
  : null,
39
43
  ],
40
- });
44
+ }), [hasTooltip, cardFavoriteChange, id, isFavorite]);
45
+ const emblem = (0, react_1.useMemo)(() => (0, utils_2.getLinkEmblem)({ icon }), [icon]);
41
46
  if (expandable?.value) {
42
- return ((0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.subcategoryTitle, "data-mobile": isMobile || undefined, children: [(0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.subcategoryTitleRow, onKeyDown: handleKeyDown, children: [(0, jsx_runtime_1.jsx)(uikit_product_title_clickable_1.TitleClickable, { as: 'a', href: service.href, onClick: handleServiceClick, innerRef: titleRef, title: service.label, icon: (0, utils_2.getLinkEmblem)(service), className: styles_module_scss_1.default.subcategoryTitleClickable, "data-test-id": titleTestId }), (0, jsx_runtime_1.jsx)(uikit_product_card_predefined_1.CardActionsSurface, { className: styles_module_scss_1.default.subcategoryTitleActions, actionsVisibility: 'always', actionsSize: isMobile ? 's' : 'm', tooltip: hasTooltip
47
+ return ((0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.subcategoryTitle, "data-mobile": isMobile || undefined, children: [(0, jsx_runtime_1.jsxs)("div", { className: styles_module_scss_1.default.subcategoryTitleRow, onKeyDown: handleKeyDown, children: [(0, jsx_runtime_1.jsx)(uikit_product_title_clickable_1.TitleClickable, { as: 'a', href: service.href, onClick: handleServiceClick, innerRef: titleRef, title: service.label, icon: emblem, className: styles_module_scss_1.default.subcategoryTitleClickable, "data-test-id": titleTestId }), (0, jsx_runtime_1.jsx)(uikit_product_card_predefined_1.CardActionsSurface, { className: styles_module_scss_1.default.subcategoryTitleActions, actionsVisibility: 'always', tooltip: hasTooltip
43
48
  ? {
44
- tip: service.description,
49
+ tip: description,
45
50
  buttonRef: tooltipTriggerRef,
46
51
  trigger: isMobile ? 'click' : 'hoverAndFocusVisible',
47
52
  'data-test-id': `${titleTestId}-tooltip`,
48
53
  }
49
- : undefined, favorite: favorite
54
+ : undefined, favorite: cardFavoriteChange
50
55
  ? {
51
56
  enabled: true,
52
57
  checked: isFavorite,
53
- onChange: favorite.onChange(service.id),
58
+ onChange: (checked) => cardFavoriteChange(id)(checked),
54
59
  buttonRef: favoriteRef,
55
60
  'data-test-id': `${titleTestId}-favorite`,
56
61
  }
57
- : undefined })] }), showDescription && ((0, jsx_runtime_1.jsx)(typography_1.Typography, { as: 'p', variant: 'body', size: 's', className: styles_module_scss_1.default.subcategoryDescription, "data-test-id": `${titleTestId}-description`, children: service.description }))] }));
62
+ : undefined })] }), showDescription && ((0, jsx_runtime_1.jsx)(typography_1.Typography, { as: 'p', variant: 'body', size: 's', className: styles_module_scss_1.default.subcategoryDescription, "data-test-id": `${titleTestId}-description`, children: description }))] }));
58
63
  }
59
64
  return (
60
65
  // Карточка — ссылка `<a>`: клик по ней бы долетал до `onClick={toggleOpen}` заголовка
61
66
  // родительского CollapseBlockTertiary (см. TODO там) и лишний раз переключал аккордеон.
62
67
  // eslint-disable-next-line jsx-a11y/no-static-element-interactions
63
- (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.subcategoryTitleDraggable, onPointerDown: utils_1.stopEventPropagation, onClick: utils_1.stopEventPropagation, children: (0, jsx_runtime_1.jsx)(ServiceCard_1.DraggableServiceCard, { groupId: groupId, service: service, favorite: favorite, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescriptionProp, dragDisabled: dragDisabled, expandable: expandable }) }));
68
+ (0, jsx_runtime_1.jsx)("div", { className: styles_module_scss_1.default.subcategoryTitleDraggable, onPointerDown: utils_1.stopEventPropagation, onClick: utils_1.stopEventPropagation, children: (0, jsx_runtime_1.jsx)(ServiceCard_1.GridServiceCard, { groupId: groupId, service: service, favoriteChecked: isFavorite, onFavoriteChange: cardFavoriteChange, isMobile: isMobile, onServiceClick: onServiceClick, showDescription: showDescriptionProp, dragEnabled: dragEnabled, expandable: expandable }) }));
64
69
  }
70
+ exports.SubCategoryTitle = (0, react_1.memo)(SubCategoryTitleBase);