@gravity-ui/page-constructor 8.23.5 → 8.24.1-alpha.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 (49) hide show
  1. package/README.md +11 -0
  2. package/build/cjs/blocks/CardLayout/CardLayout.d.ts +2 -0
  3. package/build/cjs/blocks/CardLayout/CardLayout.js +3 -2
  4. package/build/cjs/blocks/CardLayout/CardLayout.js.map +1 -1
  5. package/build/cjs/blocks/FilterBlock/FilterBlock.css +17 -0
  6. package/build/cjs/blocks/FilterBlock/FilterBlock.d.ts +1 -1
  7. package/build/cjs/blocks/FilterBlock/FilterBlock.js +43 -3
  8. package/build/cjs/blocks/FilterBlock/FilterBlock.js.map +1 -1
  9. package/build/cjs/blocks/FilterBlock/i18n/en.json +3 -1
  10. package/build/cjs/blocks/FilterBlock/i18n/index.d.ts +2 -2
  11. package/build/cjs/blocks/FilterBlock/i18n/ru.json +3 -1
  12. package/build/cjs/blocks/FilterBlock/schema.d.ts +41 -0
  13. package/build/cjs/blocks/FilterBlock/schema.js +11 -0
  14. package/build/cjs/blocks/FilterBlock/schema.js.map +1 -1
  15. package/build/cjs/blocks/Footer/components/CopyrightFloor/CopyrightFloor.css +3 -2
  16. package/build/cjs/components/FullscreenImage/FullscreenImage.css +1 -1
  17. package/build/cjs/constructor-items.d.ts +1 -1
  18. package/build/cjs/containers/PageConstructor/PageConstructor.css +7 -6
  19. package/build/cjs/models/constructor-items/blocks.d.ts +4 -0
  20. package/build/cjs/models/constructor-items/blocks.js.map +1 -1
  21. package/build/cjs/sub-blocks/PriceCard/PriceCard.css +6 -4
  22. package/build/docs/INDEX.md +1 -0
  23. package/build/docs/blocks/FilterBlock.md +76 -16
  24. package/build/esm/blocks/CardLayout/CardLayout.d.ts +2 -0
  25. package/build/esm/blocks/CardLayout/CardLayout.js +2 -2
  26. package/build/esm/blocks/CardLayout/CardLayout.js.map +1 -1
  27. package/build/esm/blocks/FilterBlock/FilterBlock.css +17 -0
  28. package/build/esm/blocks/FilterBlock/FilterBlock.d.ts +1 -1
  29. package/build/esm/blocks/FilterBlock/FilterBlock.js +43 -3
  30. package/build/esm/blocks/FilterBlock/FilterBlock.js.map +1 -1
  31. package/build/esm/blocks/FilterBlock/i18n/en.json +3 -1
  32. package/build/esm/blocks/FilterBlock/i18n/index.d.ts +2 -2
  33. package/build/esm/blocks/FilterBlock/i18n/ru.json +3 -1
  34. package/build/esm/blocks/FilterBlock/schema.d.ts +41 -0
  35. package/build/esm/blocks/FilterBlock/schema.js +11 -0
  36. package/build/esm/blocks/FilterBlock/schema.js.map +1 -1
  37. package/build/esm/blocks/Footer/components/CopyrightFloor/CopyrightFloor.css +3 -2
  38. package/build/esm/components/FullscreenImage/FullscreenImage.css +1 -1
  39. package/build/esm/constructor-items.d.ts +1 -1
  40. package/build/esm/containers/PageConstructor/PageConstructor.css +7 -6
  41. package/build/esm/models/constructor-items/blocks.d.ts +4 -0
  42. package/build/esm/models/constructor-items/blocks.js.map +1 -1
  43. package/build/esm/sub-blocks/PriceCard/PriceCard.css +6 -4
  44. package/package.json +1 -1
  45. package/schema/index.js +1 -1
  46. package/server/models/constructor-items/blocks.d.ts +4 -0
  47. package/styles/styles.css +7 -6
  48. package/styles/yfm.scss +17 -13
  49. package/widget/index.js +1 -1
@@ -28,12 +28,13 @@ unpredictable css rules order in build */
28
28
  .pc-price-card__content_theme_dark .pc-price-card__info .yfm * {
29
29
  color: var(--g-color-text-light-primary);
30
30
  }
31
- .pc-price-card__content_theme_dark .pc-price-card__info a {
31
+ .pc-price-card__content_theme_dark.pc-price-card__content_theme_dark .pc-price-card__info a {
32
32
  text-decoration: underline;
33
33
  }
34
- .pc-price-card__content_theme_dark .pc-price-card__info a:hover {
34
+ .pc-price-card__content_theme_dark.pc-price-card__content_theme_dark .pc-price-card__info a:hover {
35
35
  color: var(--g-color-text-light-secondary);
36
36
  }
37
+
37
38
  .pc-price-card__content_theme_light {
38
39
  color: var(--g-color-text-dark-primary);
39
40
  }
@@ -41,12 +42,13 @@ unpredictable css rules order in build */
41
42
  .pc-price-card__content_theme_light .pc-price-card__info .yfm * {
42
43
  color: var(--g-color-text-dark-primary);
43
44
  }
44
- .pc-price-card__content_theme_light .pc-price-card__info a {
45
+ .pc-price-card__content_theme_light.pc-price-card__content_theme_light .pc-price-card__info a {
45
46
  text-decoration: underline;
46
47
  }
47
- .pc-price-card__content_theme_light .pc-price-card__info a:hover {
48
+ .pc-price-card__content_theme_light.pc-price-card__content_theme_light .pc-price-card__info a:hover {
48
49
  color: var(--g-color-text-dark-secondary);
49
50
  }
51
+
50
52
  .pc-price-card__title.pc-price-card__title {
51
53
  font-size: var(--g-text-subheader-3-font-size);
52
54
  line-height: var(--g-text-subheader-3-line-height);
@@ -29,6 +29,7 @@ A library for rendering whole web pages or page sections from declarative JSON/Y
29
29
  - **YFM in block text needs server processing.** Markdown-like fields render as plain text unless you run content through `contentTransformer`/`fullTransform` from `@gravity-ui/page-constructor/server`; `@diplodoc/transform` is a required peer dependency.
30
30
  - **Import the SCSS styles.** Add `@gravity-ui/page-constructor/styles/styles.scss` (SCSS, not CSS); custom blocks import the same file to reuse mixins/variables.
31
31
  - **Vite needs `vite-plugin-dynamic-import`.** Dynamic block imports fail under Vite without it.
32
+ - **The grid needs a global `box-sizing: border-box` reset.** The package does not ship one; without it the container padding overflows the viewport horizontally while typecheck and build stay green. Add `*, *::before, *::after { box-sizing: border-box; }` to the host app styles.
32
33
 
33
34
  ## Install
34
35
 
@@ -68,25 +68,29 @@ Renders a set of cards grouped by tags, with a row of toggle buttons that lets t
68
68
 
69
69
  ## Properties
70
70
 
71
- | Property | Type | Default | Description |
72
- | ------------------ | ------------------------------------------------- | ------------------------- | -------------------------------------------------------------------------------------------------------------------------------- |
73
- | `title` | `string \| TitleProps` | — | Block heading (string or Title options). |
74
- | `description` | `string` | — | YFM subtitle shown under the title. |
75
- | `tags` _required_ | `FilterTag[]` | — | Tag definitions used as filter toggles (see below). |
76
- | `items` _required_ | `FilterItem[]` | — | Cards to filter (see below). |
77
- | `allTag` | `boolean \| string \| FilterTag` | — | Adds an "All" toggle. `true` uses the default label; a string overrides the label; an object supplies `{label, analyticsEvent}`. |
78
- | `tagButtonSize` | `'s' \| 'm' \| 'l' \| 'xl'` | — | Size of the filter tag buttons. |
79
- | `centered` | `boolean` | `false` | Centers the header and the tag button row. |
80
- | `colSizes` | `{all?, sm?, md?, lg?, xl?}` (each `number` 1–12) | `{all: 12, sm: 6, md: 4}` | Column width per breakpoint for a single card. |
81
- | `animated` | `boolean` | — | Enables entrance animation for the block. |
71
+ | Property | Type | Default | Description |
72
+ | -------------------- | ------------------------------------------------- | ------------------------- | -------------------------------------------------------------------------------------------------------------------------------- |
73
+ | `title` | `string \| TitleProps` | — | Block heading (string or Title options). |
74
+ | `description` | `string` | — | YFM subtitle shown under the title. |
75
+ | `tags` _required_ | `FilterTag[]` | — | Tag definitions used as filter toggles (see below). |
76
+ | `items` _required_ | `FilterItem[]` | — | Cards to filter (see below). |
77
+ | `allTag` | `boolean \| string \| FilterTag` | — | Adds an "All" toggle. `true` uses the default label; a string overrides the label; an object supplies `{label, analyticsEvent}`. |
78
+ | `tagButtonSize` | `'s' \| 'm' \| 'l' \| 'xl'` | — | Size of the filter tag buttons. |
79
+ | `centered` | `boolean` | `false` | Centers the header and the tag button row. |
80
+ | `colSizes` | `{all?, sm?, md?, lg?, xl?}` (each `number` 1–12) | `{all: 12, sm: 6, md: 4}` | Column width per breakpoint for a single card. |
81
+ | `animated` | `boolean` | — | Enables entrance animation for the block. |
82
+ | `visibleRowsCount` | `{all?, sm?, md?, lg?, xl?}` (positive integers) | Unlimited | Shared collapsed row limits for opted-in tabs; values inherit from smaller breakpoints. |
83
+ | `expandButtonText` | `string` | Localized “Show all” | Expand button label. |
84
+ | `collapseButtonText` | `string` | Localized “Show less” | Collapse button label. |
82
85
 
83
86
  ### `FilterTag`
84
87
 
85
- | Property | Type | Default | Description |
86
- | ------------------ | ---------------------- | ------- | ------------------------------------------------------------------ |
87
- | `id` _required_ | `string` | — | Tag identifier. Must match at least one value in an item's `tags`. |
88
- | `label` _required_ | `string` | — | Tag button label. |
89
- | `analyticsEvent` | `AnalyticsEventSchema` | — | Analytics event fired when the tag is selected. |
88
+ | Property | Type | Default | Description |
89
+ | ------------------ | ---------------------- | ------- | ------------------------------------------------------------------------------------------------------------------------------- |
90
+ | `id` _required_ | `string` | — | Tag identifier. Must match at least one value in an item's `tags`. |
91
+ | `label` _required_ | `string` | — | Tag button label. |
92
+ | `analyticsEvent` | `AnalyticsEventSchema` | — | Analytics event fired when the tag is selected. |
93
+ | `collapsible` | `boolean` | `false` | Enables collapsing for this tab when a matching `visibleRowsCount` limit exists. Also supported by the object form of `allTag`. |
90
94
 
91
95
  ### `FilterItem`
92
96
 
@@ -110,3 +114,59 @@ No dedicated themed props on the block itself; individual card `media`/`backgrou
110
114
  ## Storybook
111
115
 
112
116
  [FilterBlock](https://preview.gravity-ui.com/page-constructor/?path=/docs/blocks-filterblock--docs)
117
+
118
+ ## Collapsible lists
119
+
120
+ Set `collapsible: true` on each tag that should initially show a limited number of
121
+ rows, including the object form of `allTag`. This is disabled by default.
122
+ `visibleRowsCount` sets the shared row limit for these tabs, using the same
123
+ breakpoints as `colSizes`. Each value applies until the next configured breakpoint.
124
+ Without a matching row limit, the list remains unlimited.
125
+
126
+ ```yaml
127
+ allTag:
128
+ id: all
129
+ label: All services
130
+ collapsible: true
131
+ tags:
132
+ - id: infrastructure
133
+ label: Infrastructure
134
+ collapsible: true
135
+ colSizes:
136
+ all: 12
137
+ md: 6
138
+ lg: 3
139
+ visibleRowsCount:
140
+ all: 3
141
+ md: 2
142
+ lg: 2
143
+ expandButtonText: Show all
144
+ collapseButtonText: Show less
145
+ ```
146
+
147
+ Row counts must be positive integers. The number of visible cards is the row count
148
+ multiplied by the number of cards that fit in the current 12-column grid. The last
149
+ row can be incomplete when there are fewer cards remaining. The full-width normal
150
+ button appears only when the selected tab has more cards than its limit. Its labels
151
+ default to localized “Show all” / “Show less”. Changing tabs resets the expanded state.
152
+
153
+ ### Showing 8 / 9 / 8 cards
154
+
155
+ Configure row counts separately to keep complete rows as the column count changes:
156
+
157
+ ```yaml
158
+ colSizes: {all: 12, md: 6, lg: 4, xl: 3}
159
+ visibleRowsCount: {all: 3, md: 4, lg: 3, xl: 2}
160
+ ```
161
+
162
+ | Viewport width | Cards per row | Visible rows | Visible cards |
163
+ | ---------------- | ------------- | ------------ | ------------- |
164
+ | 1185px and wider | 4 | 2 | 8 |
165
+ | 1081–1184px | 3 | 3 | 9 |
166
+ | 769–1080px | 2 | 4 | 8 |
167
+ | Below 769px | 1 | 3 | 3 |
168
+
169
+ These limits apply only to tags with `collapsible: true`. They configure rows,
170
+ not automatic rounding of a requested card count. Fewer matching cards are all
171
+ shown without a toggle. See the `CollapsibleResponsiveRows` and
172
+ `CollapsibleWithFewCards` Storybook examples.
@@ -1,6 +1,8 @@
1
1
  import * as React from 'react';
2
+ import { GridColumnSizesType } from "../../grid/index.js";
2
3
  import { CardLayoutBlockProps as CardLayoutBlockParams, ClassNameProps } from "../../models/index.js";
3
4
  import './CardLayout.css';
5
+ export declare const CARD_LAYOUT_DEFAULT_SIZES: GridColumnSizesType;
4
6
  export type CardLayoutBlockProps = React.PropsWithChildren<Omit<CardLayoutBlockParams, 'children'>> & ClassNameProps;
5
7
  declare const CardLayout: ({ title, description, animated, colSizes, children, className, titleClassName, background, centered, }: CardLayoutBlockProps) => import("react/jsx-runtime").JSX.Element;
6
8
  export default CardLayout;
@@ -6,13 +6,13 @@ import { useTheme } from "../../context/theme/index.js";
6
6
  import { Col, GridJustifyContent, Row } from "../../grid/index.js";
7
7
  import { block, getThemedValue } from "../../utils/index.js";
8
8
  import './CardLayout.css';
9
- const DEFAULT_SIZES = {
9
+ export const CARD_LAYOUT_DEFAULT_SIZES = {
10
10
  all: 12,
11
11
  sm: 6,
12
12
  md: 4,
13
13
  };
14
14
  const b = block('card-layout-block');
15
- const CardLayout = ({ title, description, animated, colSizes = DEFAULT_SIZES, children, className, titleClassName, background, centered = false, }) => {
15
+ const CardLayout = ({ title, description, animated, colSizes = CARD_LAYOUT_DEFAULT_SIZES, children, className, titleClassName, background, centered = false, }) => {
16
16
  const theme = useTheme();
17
17
  const { border, ...backgroundImageProps } = getThemedValue(background || {}, theme);
18
18
  return (_jsxs(AnimateBlock, { className: b(null, className), animate: animated, children: [(title || description) && (_jsx(Title, { title: title, subtitle: description, className: b('title', { centered }, titleClassName), colJustifyContent: centered ? GridJustifyContent.Center : GridJustifyContent.Start })), _jsxs("div", { className: b('content', {
@@ -1 +1 @@
1
- {"version":3,"file":"CardLayout.js","sourceRoot":"../../../../src","sources":["blocks/CardLayout/CardLayout.tsx"],"names":[],"mappings":";AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,OAAO,OAAO,0BAAuB;AAErC,OAAO,EAAC,YAAY,EAAE,eAAe,EAAE,KAAK,EAAC,kCAAyB;AACtE,OAAO,EAAC,QAAQ,EAAC,qCAA4B;AAC7C,OAAO,EAAC,GAAG,EAAuB,kBAAkB,EAAE,GAAG,EAAC,4BAAmB;AAE7E,OAAO,EAAC,KAAK,EAAE,cAAc,EAAC,6BAAoB;AAElD,OAAO,kBAAkB,CAAC;AAE1B,MAAM,aAAa,GAAwB;IACvC,GAAG,EAAE,EAAE;IACP,EAAE,EAAE,CAAC;IACL,EAAE,EAAE,CAAC;CACR,CAAC;AAOF,MAAM,CAAC,GAAG,KAAK,CAAC,mBAAmB,CAAC,CAAC;AAErC,MAAM,UAAU,GAAG,CAAC,EAChB,KAAK,EACL,WAAW,EACX,QAAQ,EACR,QAAQ,GAAG,aAAa,EACxB,QAAQ,EACR,SAAS,EACT,cAAc,EACd,UAAU,EACV,QAAQ,GAAG,KAAK,GACG,EAAE,EAAE;IACvB,MAAM,KAAK,GAAG,QAAQ,EAAE,CAAC;IACzB,MAAM,EAAC,MAAM,EAAE,GAAG,oBAAoB,EAAC,GAAG,cAAc,CAAC,UAAU,IAAI,EAAE,EAAE,KAAK,CAAC,CAAC;IAClF,OAAO,CACH,MAAC,YAAY,IAAC,SAAS,EAAE,CAAC,CAAC,IAAI,EAAE,SAAS,CAAC,EAAE,OAAO,EAAE,QAAQ,aACzD,CAAC,KAAK,IAAI,WAAW,CAAC,IAAI,CACvB,KAAC,KAAK,IACF,KAAK,EAAE,KAAK,EACZ,QAAQ,EAAE,WAAW,EACrB,SAAS,EAAE,CAAC,CAAC,OAAO,EAAE,EAAC,QAAQ,EAAC,EAAE,cAAc,CAAC,EACjD,iBAAiB,EACb,QAAQ,CAAC,CAAC,CAAC,kBAAkB,CAAC,MAAM,CAAC,CAAC,CAAC,kBAAkB,CAAC,KAAK,GAErE,CACL,EACD,eACI,SAAS,EAAE,CAAC,CAAC,SAAS,EAAE;oBACpB,iBAAiB,EAAE,CAAC,OAAO,CAAC,UAAU,CAAC;iBAC1C,CAAC,aAEF,KAAC,eAAe,IAAC,SAAS,EAAE,CAAC,CAAC,OAAO,EAAE,EAAC,MAAM,EAAC,CAAC,KAAM,oBAAoB,GAAI,EAC9E,KAAC,GAAG,cACC,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,EAAE,CAAC,CAC5C,KAAC,GAAG,IAAa,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,CAAC,CAAC,MAAM,CAAC,YACjD,KAAK,IADA,KAAK,CAET,CACT,CAAC,GACA,IACJ,IACK,CAClB,CAAC;AACN,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC","sourcesContent":["import * as React from 'react';\n\nimport isEmpty from 'lodash/isEmpty';\n\nimport {AnimateBlock, BackgroundImage, Title} from '../../components';\nimport {useTheme} from '../../context/theme';\nimport {Col, GridColumnSizesType, GridJustifyContent, Row} from '../../grid';\nimport {CardLayoutBlockProps as CardLayoutBlockParams, ClassNameProps} from '../../models';\nimport {block, getThemedValue} from '../../utils';\n\nimport './CardLayout.scss';\n\nconst DEFAULT_SIZES: GridColumnSizesType = {\n all: 12,\n sm: 6,\n md: 4,\n};\n\nexport type CardLayoutBlockProps = React.PropsWithChildren<\n Omit<CardLayoutBlockParams, 'children'>\n> &\n ClassNameProps;\n\nconst b = block('card-layout-block');\n\nconst CardLayout = ({\n title,\n description,\n animated,\n colSizes = DEFAULT_SIZES,\n children,\n className,\n titleClassName,\n background,\n centered = false,\n}: CardLayoutBlockProps) => {\n const theme = useTheme();\n const {border, ...backgroundImageProps} = getThemedValue(background || {}, theme);\n return (\n <AnimateBlock className={b(null, className)} animate={animated}>\n {(title || description) && (\n <Title\n title={title}\n subtitle={description}\n className={b('title', {centered}, titleClassName)}\n colJustifyContent={\n centered ? GridJustifyContent.Center : GridJustifyContent.Start\n }\n />\n )}\n <div\n className={b('content', {\n 'with-background': !isEmpty(background),\n })}\n >\n <BackgroundImage className={b('image', {border})} {...backgroundImageProps} />\n <Row>\n {React.Children.map(children, (child, index) => (\n <Col key={index} sizes={colSizes} className={b('item')}>\n {child}\n </Col>\n ))}\n </Row>\n </div>\n </AnimateBlock>\n );\n};\n\nexport default CardLayout;\n"]}
1
+ {"version":3,"file":"CardLayout.js","sourceRoot":"../../../../src","sources":["blocks/CardLayout/CardLayout.tsx"],"names":[],"mappings":";AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,OAAO,OAAO,0BAAuB;AAErC,OAAO,EAAC,YAAY,EAAE,eAAe,EAAE,KAAK,EAAC,kCAAyB;AACtE,OAAO,EAAC,QAAQ,EAAC,qCAA4B;AAC7C,OAAO,EAAC,GAAG,EAAuB,kBAAkB,EAAE,GAAG,EAAC,4BAAmB;AAE7E,OAAO,EAAC,KAAK,EAAE,cAAc,EAAC,6BAAoB;AAElD,OAAO,kBAAkB,CAAC;AAE1B,MAAM,CAAC,MAAM,yBAAyB,GAAwB;IAC1D,GAAG,EAAE,EAAE;IACP,EAAE,EAAE,CAAC;IACL,EAAE,EAAE,CAAC;CACR,CAAC;AAOF,MAAM,CAAC,GAAG,KAAK,CAAC,mBAAmB,CAAC,CAAC;AAErC,MAAM,UAAU,GAAG,CAAC,EAChB,KAAK,EACL,WAAW,EACX,QAAQ,EACR,QAAQ,GAAG,yBAAyB,EACpC,QAAQ,EACR,SAAS,EACT,cAAc,EACd,UAAU,EACV,QAAQ,GAAG,KAAK,GACG,EAAE,EAAE;IACvB,MAAM,KAAK,GAAG,QAAQ,EAAE,CAAC;IACzB,MAAM,EAAC,MAAM,EAAE,GAAG,oBAAoB,EAAC,GAAG,cAAc,CAAC,UAAU,IAAI,EAAE,EAAE,KAAK,CAAC,CAAC;IAClF,OAAO,CACH,MAAC,YAAY,IAAC,SAAS,EAAE,CAAC,CAAC,IAAI,EAAE,SAAS,CAAC,EAAE,OAAO,EAAE,QAAQ,aACzD,CAAC,KAAK,IAAI,WAAW,CAAC,IAAI,CACvB,KAAC,KAAK,IACF,KAAK,EAAE,KAAK,EACZ,QAAQ,EAAE,WAAW,EACrB,SAAS,EAAE,CAAC,CAAC,OAAO,EAAE,EAAC,QAAQ,EAAC,EAAE,cAAc,CAAC,EACjD,iBAAiB,EACb,QAAQ,CAAC,CAAC,CAAC,kBAAkB,CAAC,MAAM,CAAC,CAAC,CAAC,kBAAkB,CAAC,KAAK,GAErE,CACL,EACD,eACI,SAAS,EAAE,CAAC,CAAC,SAAS,EAAE;oBACpB,iBAAiB,EAAE,CAAC,OAAO,CAAC,UAAU,CAAC;iBAC1C,CAAC,aAEF,KAAC,eAAe,IAAC,SAAS,EAAE,CAAC,CAAC,OAAO,EAAE,EAAC,MAAM,EAAC,CAAC,KAAM,oBAAoB,GAAI,EAC9E,KAAC,GAAG,cACC,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,EAAE,CAAC,CAC5C,KAAC,GAAG,IAAa,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,CAAC,CAAC,MAAM,CAAC,YACjD,KAAK,IADA,KAAK,CAET,CACT,CAAC,GACA,IACJ,IACK,CAClB,CAAC;AACN,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC","sourcesContent":["import * as React from 'react';\n\nimport isEmpty from 'lodash/isEmpty';\n\nimport {AnimateBlock, BackgroundImage, Title} from '../../components';\nimport {useTheme} from '../../context/theme';\nimport {Col, GridColumnSizesType, GridJustifyContent, Row} from '../../grid';\nimport {CardLayoutBlockProps as CardLayoutBlockParams, ClassNameProps} from '../../models';\nimport {block, getThemedValue} from '../../utils';\n\nimport './CardLayout.scss';\n\nexport const CARD_LAYOUT_DEFAULT_SIZES: GridColumnSizesType = {\n all: 12,\n sm: 6,\n md: 4,\n};\n\nexport type CardLayoutBlockProps = React.PropsWithChildren<\n Omit<CardLayoutBlockParams, 'children'>\n> &\n ClassNameProps;\n\nconst b = block('card-layout-block');\n\nconst CardLayout = ({\n title,\n description,\n animated,\n colSizes = CARD_LAYOUT_DEFAULT_SIZES,\n children,\n className,\n titleClassName,\n background,\n centered = false,\n}: CardLayoutBlockProps) => {\n const theme = useTheme();\n const {border, ...backgroundImageProps} = getThemedValue(background || {}, theme);\n return (\n <AnimateBlock className={b(null, className)} animate={animated}>\n {(title || description) && (\n <Title\n title={title}\n subtitle={description}\n className={b('title', {centered}, titleClassName)}\n colJustifyContent={\n centered ? GridJustifyContent.Center : GridJustifyContent.Start\n }\n />\n )}\n <div\n className={b('content', {\n 'with-background': !isEmpty(background),\n })}\n >\n <BackgroundImage className={b('image', {border})} {...backgroundImageProps} />\n <Row>\n {React.Children.map(children, (child, index) => (\n <Col key={index} sizes={colSizes} className={b('item')}>\n {child}\n </Col>\n ))}\n </Row>\n </div>\n </AnimateBlock>\n );\n};\n\nexport default CardLayout;\n"]}
@@ -46,4 +46,21 @@ unpredictable css rules order in build */
46
46
  }
47
47
  .pc-filter-block__cards-container {
48
48
  width: 100%;
49
+ }
50
+ .pc-filter-block__toggle {
51
+ margin-top: 24px;
52
+ padding-inline: 24px;
53
+ }
54
+ @media (min-width: 769px) {
55
+ .pc-filter-block.pc-AnimateBlock .pc-filter-block__toggle, .pc-AnimateBlock .pc-filter-block .pc-filter-block__toggle {
56
+ position: relative;
57
+ top: 100px;
58
+ opacity: 0;
59
+ }
60
+ .pc-filter-block.pc-AnimateBlock.animate .pc-filter-block__toggle, .pc-AnimateBlock .pc-filter-block.animate .pc-filter-block__toggle {
61
+ top: 0;
62
+ opacity: 1;
63
+ transition: top 0.8s cubic-bezier(0.25, 0.46, 0.45, 0.94), opacity 0.8s cubic-bezier(0.25, 0.46, 0.45, 0.94);
64
+ transition-delay: 0s;
65
+ }
49
66
  }
@@ -1,4 +1,4 @@
1
1
  import { FilterBlockProps } from "../../models/index.js";
2
2
  import './FilterBlock.css';
3
- declare const FilterBlock: ({ title, description, tags, tagButtonSize, allTag, items, colSizes, centered, animated, }: FilterBlockProps) => import("react/jsx-runtime").JSX.Element;
3
+ declare const FilterBlock: ({ title, description, tags, tagButtonSize, allTag, items, colSizes, visibleRowsCount, expandButtonText, collapseButtonText, centered, animated, }: FilterBlockProps) => import("react/jsx-runtime").JSX.Element;
4
4
  export default FilterBlock;
@@ -1,17 +1,39 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import * as React from 'react';
3
- import { CardLayoutBlock } from "../index.js";
3
+ import { Button } from '@gravity-ui/uikit';
4
4
  import { AnimateBlock, Title } from "../../components/index.js";
5
5
  import ButtonTabs from "../../components/ButtonTabs/ButtonTabs.js";
6
+ import { BREAKPOINTS } from "../../constants.js";
6
7
  import { ConstructorItem } from "../../containers/PageConstructor/components/ConstructorItem/index.js";
8
+ import { useWindowWidth } from "../../context/windowWidthContext/index.js";
7
9
  import { Col, Row } from "../../grid/index.js";
10
+ import { GridColumnSize } from "../../grid/types.js";
8
11
  import { useAnalytics } from "../../hooks/index.js";
9
12
  import { block, getBlockKey } from "../../utils/index.js";
13
+ import CardLayoutBlock, { CARD_LAYOUT_DEFAULT_SIZES } from "../CardLayout/CardLayout.js";
10
14
  import { i18n } from "./i18n/index.js";
11
15
  import './FilterBlock.css';
12
16
  const b = block('filter-block');
13
- const FilterBlock = ({ title, description, tags, tagButtonSize, allTag, items, colSizes, centered, animated, }) => {
17
+ const GRID_COLUMN_SIZES = [
18
+ GridColumnSize.Sm,
19
+ GridColumnSize.Md,
20
+ GridColumnSize.Lg,
21
+ GridColumnSize.Xl,
22
+ ];
23
+ function responsiveValue({ values, width, fallback }) {
24
+ let result = values.all ?? fallback;
25
+ for (const size of GRID_COLUMN_SIZES) {
26
+ const value = values[size];
27
+ if (width >= BREAKPOINTS[size] && value !== undefined) {
28
+ result = value;
29
+ }
30
+ }
31
+ return result;
32
+ }
33
+ const FilterBlock = ({ title, description, tags, tagButtonSize, allTag, items, colSizes, visibleRowsCount, expandButtonText, collapseButtonText, centered, animated, }) => {
14
34
  const handleAnalytics = useAnalytics();
35
+ const width = useWindowWidth();
36
+ const [expanded, setExpanded] = React.useState(false);
15
37
  const tabButtons = React.useMemo(() => {
16
38
  let allButton;
17
39
  if (allTag) {
@@ -49,6 +71,9 @@ const FilterBlock = ({ title, description, tags, tagButtonSize, allTag, items, c
49
71
  ? tabButtons[0].id
50
72
  : selectedTag;
51
73
  }, [tabButtons, selectedTag]);
74
+ React.useEffect(() => {
75
+ setExpanded(false);
76
+ }, [actualTag]);
52
77
  const cards = React.useMemo(() => {
53
78
  const itemsWithKeys = items.map((item, index) => ({
54
79
  ...item,
@@ -58,6 +83,19 @@ const FilterBlock = ({ title, description, tags, tagButtonSize, allTag, items, c
58
83
  ? itemsWithKeys.filter((item) => item.tags.includes(actualTag))
59
84
  : itemsWithKeys;
60
85
  }, [actualTag, items]);
86
+ // Only the active tab's configuration determines whether its cards can be collapsed.
87
+ const allTagConfig = typeof allTag === 'object' ? allTag : undefined;
88
+ const activeTag = actualTag === null ? allTagConfig : tags?.find((tag) => tag.id === actualTag);
89
+ const rows = responsiveValue({ values: visibleRowsCount ?? {}, width, fallback: Infinity });
90
+ const columns = Math.max(1, Math.floor(12 /
91
+ responsiveValue({
92
+ values: colSizes ?? CARD_LAYOUT_DEFAULT_SIZES,
93
+ width,
94
+ fallback: 12,
95
+ })));
96
+ const limit = rows > 0 ? Math.floor(rows) * columns : Infinity;
97
+ const canCollapse = Boolean(activeTag?.collapsible && cards.length > limit);
98
+ const visibleCards = canCollapse && !expanded ? cards.slice(0, limit) : cards;
61
99
  const handleSelectTab = React.useCallback((tabId) => {
62
100
  setSelectedTag(tabId);
63
101
  const tabButton = tabButtons.find((tab) => tab.id === tabId);
@@ -65,7 +103,9 @@ const FilterBlock = ({ title, description, tags, tagButtonSize, allTag, items, c
65
103
  handleAnalytics(tabButton.analyticsEvent);
66
104
  }
67
105
  }, [tabButtons, handleAnalytics]);
68
- return (_jsxs(AnimateBlock, { className: b(), animate: animated, children: [title && (_jsx(Title, { className: b('title', { centered: centered }), title: title, subtitle: description })), tabButtons.length && (_jsx(Row, { children: _jsx(Col, { children: _jsx(ButtonTabs, { className: b('tabs', { centered: centered }), items: tabButtons, activeTab: selectedTag, onSelectTab: handleSelectTab, tabSize: tagButtonSize }) }) })), _jsx(Row, { className: b('block-container'), children: _jsx(CardLayoutBlock, { title: "", colSizes: colSizes, className: b('cards-container'), children: cards.map(({ card, key }) => (_jsx(ConstructorItem, { data: card, blockKey: key }, key))) }) })] }));
106
+ return (_jsxs(AnimateBlock, { className: b(), animate: animated, children: [title && (_jsx(Title, { className: b('title', { centered: centered }), title: title, subtitle: description })), tabButtons.length && (_jsx(Row, { children: _jsx(Col, { children: _jsx(ButtonTabs, { className: b('tabs', { centered: centered }), items: tabButtons, activeTab: actualTag, onSelectTab: handleSelectTab, tabSize: tagButtonSize }) }) })), _jsx(Row, { className: b('block-container'), children: _jsx(CardLayoutBlock, { title: "", colSizes: colSizes, className: b('cards-container'), animated: animated, children: visibleCards.map(({ card, key }) => (_jsx(ConstructorItem, { data: card, blockKey: key }, key))) }) }), canCollapse && (_jsx(Button, { className: b('toggle'), style: { transitionDelay: `${Math.min(visibleCards.length, 99) * 0.1}s` }, view: "normal", size: "xl", width: "max", "aria-expanded": expanded, onClick: () => setExpanded((value) => !value), children: expanded
107
+ ? (collapseButtonText ?? i18n('label-collapse'))
108
+ : (expandButtonText ?? i18n('label-expand')) }))] }));
69
109
  };
70
110
  export default FilterBlock;
71
111
  //# sourceMappingURL=FilterBlock.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"FilterBlock.js","sourceRoot":"../../../../src","sources":["blocks/FilterBlock/FilterBlock.tsx"],"names":[],"mappings":";AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,OAAO,EAAC,eAAe,EAAC,oBAAW;AACnC,OAAO,EAAC,YAAY,EAAE,KAAK,EAAC,kCAAyB;AACrD,OAAO,UAAiC,kDAA+C;AACvF,OAAO,EAAC,eAAe,EAAC,6EAAoE;AAC5F,OAAO,EAAC,GAAG,EAAE,GAAG,EAAC,4BAAmB;AACpC,OAAO,EAAC,YAAY,EAAC,6BAAoB;AAEzC,OAAO,EAAC,KAAK,EAAE,WAAW,EAAC,6BAAoB;AAE/C,OAAO,EAAC,IAAI,EAAC,wBAAe;AAE5B,OAAO,mBAAmB,CAAC;AAE3B,MAAM,CAAC,GAAG,KAAK,CAAC,cAAc,CAAC,CAAC;AAEhC,MAAM,WAAW,GAAG,CAAC,EACjB,KAAK,EACL,WAAW,EACX,IAAI,EACJ,aAAa,EACb,MAAM,EACN,KAAK,EACL,QAAQ,EACR,QAAQ,EACR,QAAQ,GACO,EAAE,EAAE;IACnB,MAAM,eAAe,GAAG,YAAY,EAAE,CAAC;IACvC,MAAM,UAAU,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,EAAE;QAClC,IAAI,SAA0C,CAAC;QAC/C,IAAI,MAAM,EAAE,CAAC;YACT,IAAI,OAAO,MAAM,KAAK,SAAS,EAAE,CAAC;gBAC9B,SAAS,GAAG;oBACR,EAAE,EAAE,IAAI;oBACR,KAAK,EAAE,IAAI,CAAC,eAAe,CAAC;iBAC/B,CAAC;YACN,CAAC;iBAAM,IAAI,OAAO,MAAM,KAAK,QAAQ,EAAE,CAAC;gBACpC,SAAS,GAAG;oBACR,EAAE,EAAE,IAAI;oBACR,KAAK,EAAE,MAAM;iBAChB,CAAC;YACN,CAAC;iBAAM,IAAI,OAAO,MAAM,KAAK,QAAQ,EAAE,CAAC;gBACpC,SAAS,GAAG;oBACR,EAAE,EAAE,IAAI;oBACR,KAAK,EAAE,MAAM,CAAC,KAAK;oBACnB,cAAc,EAAE,MAAM,CAAC,cAAc;iBACxC,CAAC;YACN,CAAC;QACL,CAAC;QACD,MAAM,YAAY,GACd,IAAI;YACJ,IAAI,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;gBACf,EAAE,EAAE,GAAG,CAAC,EAAE;gBACV,KAAK,EAAE,GAAG,CAAC,KAAK;gBAChB,cAAc,EAAE,GAAG,CAAC,cAAc;aACrC,CAAC,CAAC,CAAC;QACR,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,CAAC,YAAY,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IACtF,CAAC,EAAE,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC,CAAC;IAEnB,MAAM,CAAC,WAAW,EAAE,cAAc,CAAC,GAAG,KAAK,CAAC,QAAQ,CAChD,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAC9C,CAAC;IAEF,MAAM,SAAS,GAAkB,KAAK,CAAC,OAAO,CAAC,GAAG,EAAE;QAChD,OAAO,UAAU,CAAC,MAAM,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,EAAE,KAAK,WAAW,CAAC;YACzE,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,EAAE;YAClB,CAAC,CAAC,WAAW,CAAC;IACtB,CAAC,EAAE,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC,CAAC;IAE9B,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,EAAE;QAC7B,MAAM,aAAa,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC,CAAC;YAC9C,GAAG,IAAI;YACP,GAAG,EAAE,WAAW,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC;SACrC,CAAC,CAAC,CAAC;QAEJ,OAAO,SAAS;YACZ,CAAC,CAAC,aAAa,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,SAAS,CAAC,CAAC;YAC/D,CAAC,CAAC,aAAa,CAAC;IACxB,CAAC,EAAE,CAAC,SAAS,EAAE,KAAK,CAAC,CAAC,CAAC;IAEvB,MAAM,eAAe,GAAG,KAAK,CAAC,WAAW,CACrC,CAAC,KAAoB,EAAE,EAAE;QACrB,cAAc,CAAC,KAAK,CAAC,CAAC;QAEtB,MAAM,SAAS,GAAG,UAAU,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,EAAE,KAAK,KAAK,CAAC,CAAC;QAC7D,IAAI,SAAS,EAAE,cAAc,EAAE,CAAC;YAC5B,eAAe,CAAC,SAAS,CAAC,cAAc,CAAC,CAAC;QAC9C,CAAC;IACL,CAAC,EACD,CAAC,UAAU,EAAE,eAAe,CAAC,CAChC,CAAC;IAEF,OAAO,CACH,MAAC,YAAY,IAAC,SAAS,EAAE,CAAC,EAAE,EAAE,OAAO,EAAE,QAAQ,aAC1C,KAAK,IAAI,CACN,KAAC,KAAK,IACF,SAAS,EAAE,CAAC,CAAC,OAAO,EAAE,EAAC,QAAQ,EAAE,QAAQ,EAAC,CAAC,EAC3C,KAAK,EAAE,KAAK,EACZ,QAAQ,EAAE,WAAW,GACvB,CACL,EACA,UAAU,CAAC,MAAM,IAAI,CAClB,KAAC,GAAG,cACA,KAAC,GAAG,cACA,KAAC,UAAU,IACP,SAAS,EAAE,CAAC,CAAC,MAAM,EAAE,EAAC,QAAQ,EAAE,QAAQ,EAAC,CAAC,EAC1C,KAAK,EAAE,UAAU,EACjB,SAAS,EAAE,WAAW,EACtB,WAAW,EAAE,eAAe,EAC5B,OAAO,EAAE,aAAa,GACxB,GACA,GACJ,CACT,EACD,KAAC,GAAG,IAAC,SAAS,EAAE,CAAC,CAAC,iBAAiB,CAAC,YAChC,KAAC,eAAe,IAAC,KAAK,EAAC,EAAE,EAAC,QAAQ,EAAE,QAAQ,EAAE,SAAS,EAAE,CAAC,CAAC,iBAAiB,CAAC,YACxE,KAAK,CAAC,GAAG,CAAC,CAAC,EAAC,IAAI,EAAE,GAAG,EAAC,EAAE,EAAE,CAAC,CACxB,KAAC,eAAe,IAAC,IAAI,EAAE,IAAI,EAAE,QAAQ,EAAE,GAAG,IAAO,GAAG,CAAI,CAC3D,CAAC,GACY,GAChB,IACK,CAClB,CAAC;AACN,CAAC,CAAC;AACF,eAAe,WAAW,CAAC","sourcesContent":["import * as React from 'react';\n\nimport {CardLayoutBlock} from '..';\nimport {AnimateBlock, Title} from '../../components';\nimport ButtonTabs, {ButtonTabsItemProps} from '../../components/ButtonTabs/ButtonTabs';\nimport {ConstructorItem} from '../../containers/PageConstructor/components/ConstructorItem';\nimport {Col, Row} from '../../grid';\nimport {useAnalytics} from '../../hooks';\nimport {FilterBlockProps} from '../../models';\nimport {block, getBlockKey} from '../../utils';\n\nimport {i18n} from './i18n';\n\nimport './FilterBlock.scss';\n\nconst b = block('filter-block');\n\nconst FilterBlock = ({\n title,\n description,\n tags,\n tagButtonSize,\n allTag,\n items,\n colSizes,\n centered,\n animated,\n}: FilterBlockProps) => {\n const handleAnalytics = useAnalytics();\n const tabButtons = React.useMemo(() => {\n let allButton: ButtonTabsItemProps | undefined;\n if (allTag) {\n if (typeof allTag === 'boolean') {\n allButton = {\n id: null,\n title: i18n('label-all-tag'),\n };\n } else if (typeof allTag === 'string') {\n allButton = {\n id: null,\n title: allTag,\n };\n } else if (typeof allTag === 'object') {\n allButton = {\n id: null,\n title: allTag.label,\n analyticsEvent: allTag.analyticsEvent,\n };\n }\n }\n const otherButtons: ButtonTabsItemProps[] | undefined =\n tags &&\n tags.map((tag) => ({\n id: tag.id,\n title: tag.label,\n analyticsEvent: tag.analyticsEvent,\n }));\n return [...(allButton ? [allButton] : []), ...(otherButtons ? otherButtons : [])];\n }, [allTag, tags]);\n\n const [selectedTag, setSelectedTag] = React.useState(\n tabButtons.length ? tabButtons[0].id : null,\n );\n\n const actualTag: string | null = React.useMemo(() => {\n return tabButtons.length && !tabButtons.find((tab) => tab.id === selectedTag)\n ? tabButtons[0].id\n : selectedTag;\n }, [tabButtons, selectedTag]);\n\n const cards = React.useMemo(() => {\n const itemsWithKeys = items.map((item, index) => ({\n ...item,\n key: getBlockKey(item.card, index),\n }));\n\n return actualTag\n ? itemsWithKeys.filter((item) => item.tags.includes(actualTag))\n : itemsWithKeys;\n }, [actualTag, items]);\n\n const handleSelectTab = React.useCallback(\n (tabId: string | null) => {\n setSelectedTag(tabId);\n\n const tabButton = tabButtons.find((tab) => tab.id === tabId);\n if (tabButton?.analyticsEvent) {\n handleAnalytics(tabButton.analyticsEvent);\n }\n },\n [tabButtons, handleAnalytics],\n );\n\n return (\n <AnimateBlock className={b()} animate={animated}>\n {title && (\n <Title\n className={b('title', {centered: centered})}\n title={title}\n subtitle={description}\n />\n )}\n {tabButtons.length && (\n <Row>\n <Col>\n <ButtonTabs\n className={b('tabs', {centered: centered})}\n items={tabButtons}\n activeTab={selectedTag}\n onSelectTab={handleSelectTab}\n tabSize={tagButtonSize}\n />\n </Col>\n </Row>\n )}\n <Row className={b('block-container')}>\n <CardLayoutBlock title=\"\" colSizes={colSizes} className={b('cards-container')}>\n {cards.map(({card, key}) => (\n <ConstructorItem data={card} blockKey={key} key={key} />\n ))}\n </CardLayoutBlock>\n </Row>\n </AnimateBlock>\n );\n};\nexport default FilterBlock;\n"]}
1
+ {"version":3,"file":"FilterBlock.js","sourceRoot":"../../../../src","sources":["blocks/FilterBlock/FilterBlock.tsx"],"names":[],"mappings":"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","sourcesContent":["import * as React from 'react';\n\nimport {Button} from '@gravity-ui/uikit';\n\nimport {AnimateBlock, Title} from '../../components';\nimport ButtonTabs, {ButtonTabsItemProps} from '../../components/ButtonTabs/ButtonTabs';\nimport {BREAKPOINTS} from '../../constants';\nimport {ConstructorItem} from '../../containers/PageConstructor/components/ConstructorItem';\nimport {useWindowWidth} from '../../context/windowWidthContext';\nimport {Col, Row} from '../../grid';\nimport {GridColumnSize, GridColumnSizesType} from '../../grid/types';\nimport {useAnalytics} from '../../hooks';\nimport {FilterBlockProps} from '../../models';\nimport {block, getBlockKey} from '../../utils';\nimport CardLayoutBlock, {CARD_LAYOUT_DEFAULT_SIZES} from '../CardLayout/CardLayout';\n\nimport {i18n} from './i18n';\n\nimport './FilterBlock.scss';\n\nconst b = block('filter-block');\n\nconst GRID_COLUMN_SIZES = [\n GridColumnSize.Sm,\n GridColumnSize.Md,\n GridColumnSize.Lg,\n GridColumnSize.Xl,\n] as const;\n\ntype ResponsiveValueParams = {\n values: GridColumnSizesType;\n width: number;\n fallback: number;\n};\n\nfunction responsiveValue({values, width, fallback}: ResponsiveValueParams) {\n let result = values.all ?? fallback;\n\n for (const size of GRID_COLUMN_SIZES) {\n const value = values[size];\n\n if (width >= BREAKPOINTS[size] && value !== undefined) {\n result = value;\n }\n }\n\n return result;\n}\n\nconst FilterBlock = ({\n title,\n description,\n tags,\n tagButtonSize,\n allTag,\n items,\n colSizes,\n visibleRowsCount,\n expandButtonText,\n collapseButtonText,\n centered,\n animated,\n}: FilterBlockProps) => {\n const handleAnalytics = useAnalytics();\n const width = useWindowWidth();\n const [expanded, setExpanded] = React.useState(false);\n const tabButtons = React.useMemo(() => {\n let allButton: ButtonTabsItemProps | undefined;\n if (allTag) {\n if (typeof allTag === 'boolean') {\n allButton = {\n id: null,\n title: i18n('label-all-tag'),\n };\n } else if (typeof allTag === 'string') {\n allButton = {\n id: null,\n title: allTag,\n };\n } else if (typeof allTag === 'object') {\n allButton = {\n id: null,\n title: allTag.label,\n analyticsEvent: allTag.analyticsEvent,\n };\n }\n }\n const otherButtons: ButtonTabsItemProps[] | undefined =\n tags &&\n tags.map((tag) => ({\n id: tag.id,\n title: tag.label,\n analyticsEvent: tag.analyticsEvent,\n }));\n return [...(allButton ? [allButton] : []), ...(otherButtons ? otherButtons : [])];\n }, [allTag, tags]);\n\n const [selectedTag, setSelectedTag] = React.useState(\n tabButtons.length ? tabButtons[0].id : null,\n );\n\n const actualTag: string | null = React.useMemo(() => {\n return tabButtons.length && !tabButtons.find((tab) => tab.id === selectedTag)\n ? tabButtons[0].id\n : selectedTag;\n }, [tabButtons, selectedTag]);\n\n React.useEffect(() => {\n setExpanded(false);\n }, [actualTag]);\n\n const cards = React.useMemo(() => {\n const itemsWithKeys = items.map((item, index) => ({\n ...item,\n key: getBlockKey(item.card, index),\n }));\n\n return actualTag\n ? itemsWithKeys.filter((item) => item.tags.includes(actualTag))\n : itemsWithKeys;\n }, [actualTag, items]);\n\n // Only the active tab's configuration determines whether its cards can be collapsed.\n const allTagConfig = typeof allTag === 'object' ? allTag : undefined;\n const activeTag = actualTag === null ? allTagConfig : tags?.find((tag) => tag.id === actualTag);\n const rows = responsiveValue({values: visibleRowsCount ?? {}, width, fallback: Infinity});\n const columns = Math.max(\n 1,\n Math.floor(\n 12 /\n responsiveValue({\n values: colSizes ?? CARD_LAYOUT_DEFAULT_SIZES,\n width,\n fallback: 12,\n }),\n ),\n );\n const limit = rows > 0 ? Math.floor(rows) * columns : Infinity;\n const canCollapse = Boolean(activeTag?.collapsible && cards.length > limit);\n const visibleCards = canCollapse && !expanded ? cards.slice(0, limit) : cards;\n\n const handleSelectTab = React.useCallback(\n (tabId: string | null) => {\n setSelectedTag(tabId);\n\n const tabButton = tabButtons.find((tab) => tab.id === tabId);\n if (tabButton?.analyticsEvent) {\n handleAnalytics(tabButton.analyticsEvent);\n }\n },\n [tabButtons, handleAnalytics],\n );\n\n return (\n <AnimateBlock className={b()} animate={animated}>\n {title && (\n <Title\n className={b('title', {centered: centered})}\n title={title}\n subtitle={description}\n />\n )}\n {tabButtons.length && (\n <Row>\n <Col>\n <ButtonTabs\n className={b('tabs', {centered: centered})}\n items={tabButtons}\n activeTab={actualTag}\n onSelectTab={handleSelectTab}\n tabSize={tagButtonSize}\n />\n </Col>\n </Row>\n )}\n <Row className={b('block-container')}>\n <CardLayoutBlock\n title=\"\"\n colSizes={colSizes}\n className={b('cards-container')}\n animated={animated}\n >\n {visibleCards.map(({card, key}) => (\n <ConstructorItem data={card} blockKey={key} key={key} />\n ))}\n </CardLayoutBlock>\n </Row>\n {canCollapse && (\n <Button\n className={b('toggle')}\n style={{transitionDelay: `${Math.min(visibleCards.length, 99) * 0.1}s`}}\n view=\"normal\"\n size=\"xl\"\n width=\"max\"\n aria-expanded={expanded}\n onClick={() => setExpanded((value) => !value)}\n >\n {expanded\n ? (collapseButtonText ?? i18n('label-collapse'))\n : (expandButtonText ?? i18n('label-expand'))}\n </Button>\n )}\n </AnimateBlock>\n );\n};\nexport default FilterBlock;\n"]}
@@ -1,3 +1,5 @@
1
1
  {
2
- "label-all-tag": "All"
2
+ "label-all-tag": "All",
3
+ "label-expand": "Show all",
4
+ "label-collapse": "Show less"
3
5
  }
@@ -1,5 +1,5 @@
1
- export declare const i18n: ((key: "label-all-tag", params?: import("@gravity-ui/i18n").Params) => string) & {
1
+ export declare const i18n: ((key: "label-all-tag" | "label-expand" | "label-collapse", params?: import("@gravity-ui/i18n").Params) => string) & {
2
2
  keysetData: {
3
- "pc-FilterBlock": Record<"label-all-tag", import("@gravity-ui/i18n").KeyData>;
3
+ "pc-FilterBlock": Record<"label-all-tag" | "label-expand" | "label-collapse", import("@gravity-ui/i18n").KeyData>;
4
4
  };
5
5
  };
@@ -1,3 +1,5 @@
1
1
  {
2
- "label-all-tag": "Все"
2
+ "label-all-tag": "Все",
3
+ "label-expand": "Смотреть всё",
4
+ "label-collapse": "Свернуть"
3
5
  }
@@ -46,6 +46,9 @@ export declare const FilterTagProps: {
46
46
  };
47
47
  };
48
48
  };
49
+ collapsible: {
50
+ type: string;
51
+ };
49
52
  };
50
53
  };
51
54
  export declare const FilterItemProps: {
@@ -119,6 +122,9 @@ export declare const FilterProps: {
119
122
  };
120
123
  };
121
124
  };
125
+ collapsible: {
126
+ type: string;
127
+ };
122
128
  };
123
129
  optionName?: undefined;
124
130
  })[];
@@ -128,6 +134,22 @@ export declare const FilterProps: {
128
134
  additionalProperties: boolean;
129
135
  properties: {};
130
136
  };
137
+ visibleRowsCount: {
138
+ type: string;
139
+ additionalProperties: boolean;
140
+ properties: {
141
+ [k: string]: {
142
+ type: string;
143
+ minimum: number;
144
+ };
145
+ };
146
+ };
147
+ expandButtonText: {
148
+ type: string;
149
+ };
150
+ collapseButtonText: {
151
+ type: string;
152
+ };
131
153
  tags: {
132
154
  type: string;
133
155
  items: {
@@ -387,6 +409,9 @@ export declare const FilterBlock: {
387
409
  };
388
410
  };
389
411
  };
412
+ collapsible: {
413
+ type: string;
414
+ };
390
415
  };
391
416
  optionName?: undefined;
392
417
  })[];
@@ -396,6 +421,22 @@ export declare const FilterBlock: {
396
421
  additionalProperties: boolean;
397
422
  properties: {};
398
423
  };
424
+ visibleRowsCount: {
425
+ type: string;
426
+ additionalProperties: boolean;
427
+ properties: {
428
+ [k: string]: {
429
+ type: string;
430
+ minimum: number;
431
+ };
432
+ };
433
+ };
434
+ expandButtonText: {
435
+ type: string;
436
+ };
437
+ collapseButtonText: {
438
+ type: string;
439
+ };
399
440
  tags: {
400
441
  type: string;
401
442
  items: {
@@ -13,6 +13,7 @@ export const FilterTagProps = {
13
13
  type: 'string',
14
14
  },
15
15
  analyticsEvent: AnalyticsEventSchema,
16
+ collapsible: { type: 'boolean' },
16
17
  },
17
18
  };
18
19
  export const FilterItemProps = {
@@ -51,6 +52,16 @@ export const FilterProps = {
51
52
  ],
52
53
  },
53
54
  colSizes: containerSizesObject,
55
+ visibleRowsCount: {
56
+ type: 'object',
57
+ additionalProperties: false,
58
+ properties: Object.fromEntries(['all', 'sm', 'md', 'lg', 'xl'].map((size) => [
59
+ size,
60
+ { type: 'integer', minimum: 1 },
61
+ ])),
62
+ },
63
+ expandButtonText: { type: 'string' },
64
+ collapseButtonText: { type: 'string' },
54
65
  tags: filteredArray(FilterTagProps),
55
66
  items: filteredArray(FilterItemProps),
56
67
  tagButtonSize: {
@@ -1 +1 @@
1
- {"version":3,"file":"schema.js","sourceRoot":"../../../../src","sources":["blocks/FilterBlock/schema.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,eAAe,EACf,cAAc,EACd,gBAAgB,EAChB,oBAAoB,GACvB,0CAAuC;AACxC,OAAO,EAAC,oBAAoB,EAAC,yCAAsC;AACnE,OAAO,EAAC,aAAa,EAAC,yCAAsC;AAE5D,MAAM,CAAC,MAAM,cAAc,GAAG;IAC1B,IAAI,EAAE,QAAQ;IACd,oBAAoB,EAAE,KAAK;IAC3B,QAAQ,EAAE,CAAC,IAAI,EAAE,OAAO,CAAC;IACzB,UAAU,EAAE;QACR,EAAE,EAAE;YACA,IAAI,EAAE,QAAQ;SACjB;QACD,KAAK,EAAE;YACH,IAAI,EAAE,QAAQ;SACjB;QACD,cAAc,EAAE,oBAAoB;KACvC;CACJ,CAAC;AAEF,MAAM,CAAC,MAAM,eAAe,GAAG;IAC3B,oBAAoB,EAAE,KAAK;IAC3B,QAAQ,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC;IAC1B,UAAU,EAAE;QACR,IAAI,EAAE;YACF,IAAI,EAAE,OAAO;YACb,KAAK,EAAE;gBACH,IAAI,EAAE,QAAQ;aACjB;SACJ;QACD,IAAI,EAAE,EAAC,IAAI,EAAE,yBAAyB,EAAC;KAC1C;CACJ,CAAC;AAEF,MAAM,CAAC,MAAM,WAAW,GAAG;IACvB,oBAAoB,EAAE,KAAK;IAC3B,QAAQ,EAAE,CAAC,MAAM,EAAE,OAAO,CAAC;IAC3B,UAAU,EAAE;QACR,GAAG,cAAc;QACjB,GAAG,eAAe;QAClB,GAAG,gBAAgB;QACnB,MAAM,EAAE;YACJ,KAAK,EAAE;gBACH;oBACI,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,MAAM;iBACrB;gBACD;oBACI,IAAI,EAAE,QAAQ;oBACd,UAAU,EAAE,OAAO;iBACtB;gBACD;oBACI,GAAG,cAAc;iBACpB;aACJ;SACJ;QACD,QAAQ,EAAE,oBAAoB;QAC9B,IAAI,EAAE,aAAa,CAAC,cAAc,CAAC;QACnC,KAAK,EAAE,aAAa,CAAC,eAAe,CAAC;QACrC,aAAa,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,IAAI,EAAE,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,CAAC;SAC9B;QACD,QAAQ,EAAE,EAAC,IAAI,EAAE,SAAS,EAAC;KAC9B;CACJ,CAAC;AAEF,MAAM,CAAC,MAAM,WAAW,GAAG;IACvB,cAAc,EAAE,WAAW;CAC9B,CAAC","sourcesContent":["import {\n AnimatableProps,\n BlockBaseProps,\n BlockHeaderProps,\n containerSizesObject,\n} from '../../schema/validators/common';\nimport {AnalyticsEventSchema} from '../../schema/validators/event';\nimport {filteredArray} from '../../schema/validators/utils';\n\nexport const FilterTagProps = {\n type: 'object',\n additionalProperties: false,\n required: ['id', 'label'],\n properties: {\n id: {\n type: 'string',\n },\n label: {\n type: 'string',\n },\n analyticsEvent: AnalyticsEventSchema,\n },\n};\n\nexport const FilterItemProps = {\n additionalProperties: false,\n required: ['tags', 'card'],\n properties: {\n tags: {\n type: 'array',\n items: {\n type: 'string',\n },\n },\n card: {$ref: 'self#/definitions/cards'},\n },\n};\n\nexport const FilterProps = {\n additionalProperties: false,\n required: ['tags', 'items'],\n properties: {\n ...BlockBaseProps,\n ...AnimatableProps,\n ...BlockHeaderProps,\n allTag: {\n oneOf: [\n {\n type: 'boolean',\n optionName: 'auto',\n },\n {\n type: 'string',\n optionName: 'cutom',\n },\n {\n ...FilterTagProps,\n },\n ],\n },\n colSizes: containerSizesObject,\n tags: filteredArray(FilterTagProps),\n items: filteredArray(FilterItemProps),\n tagButtonSize: {\n type: 'string',\n enum: ['s', 'm', 'l', 'xl'],\n },\n centered: {type: 'boolean'},\n },\n};\n\nexport const FilterBlock = {\n 'filter-block': FilterProps,\n};\n"]}
1
+ {"version":3,"file":"schema.js","sourceRoot":"../../../../src","sources":["blocks/FilterBlock/schema.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,eAAe,EACf,cAAc,EACd,gBAAgB,EAChB,oBAAoB,GACvB,0CAAuC;AACxC,OAAO,EAAC,oBAAoB,EAAC,yCAAsC;AACnE,OAAO,EAAC,aAAa,EAAC,yCAAsC;AAE5D,MAAM,CAAC,MAAM,cAAc,GAAG;IAC1B,IAAI,EAAE,QAAQ;IACd,oBAAoB,EAAE,KAAK;IAC3B,QAAQ,EAAE,CAAC,IAAI,EAAE,OAAO,CAAC;IACzB,UAAU,EAAE;QACR,EAAE,EAAE;YACA,IAAI,EAAE,QAAQ;SACjB;QACD,KAAK,EAAE;YACH,IAAI,EAAE,QAAQ;SACjB;QACD,cAAc,EAAE,oBAAoB;QACpC,WAAW,EAAE,EAAC,IAAI,EAAE,SAAS,EAAC;KACjC;CACJ,CAAC;AAEF,MAAM,CAAC,MAAM,eAAe,GAAG;IAC3B,oBAAoB,EAAE,KAAK;IAC3B,QAAQ,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC;IAC1B,UAAU,EAAE;QACR,IAAI,EAAE;YACF,IAAI,EAAE,OAAO;YACb,KAAK,EAAE;gBACH,IAAI,EAAE,QAAQ;aACjB;SACJ;QACD,IAAI,EAAE,EAAC,IAAI,EAAE,yBAAyB,EAAC;KAC1C;CACJ,CAAC;AAEF,MAAM,CAAC,MAAM,WAAW,GAAG;IACvB,oBAAoB,EAAE,KAAK;IAC3B,QAAQ,EAAE,CAAC,MAAM,EAAE,OAAO,CAAC;IAC3B,UAAU,EAAE;QACR,GAAG,cAAc;QACjB,GAAG,eAAe;QAClB,GAAG,gBAAgB;QACnB,MAAM,EAAE;YACJ,KAAK,EAAE;gBACH;oBACI,IAAI,EAAE,SAAS;oBACf,UAAU,EAAE,MAAM;iBACrB;gBACD;oBACI,IAAI,EAAE,QAAQ;oBACd,UAAU,EAAE,OAAO;iBACtB;gBACD;oBACI,GAAG,cAAc;iBACpB;aACJ;SACJ;QACD,QAAQ,EAAE,oBAAoB;QAC9B,gBAAgB,EAAE;YACd,IAAI,EAAE,QAAQ;YACd,oBAAoB,EAAE,KAAK;YAC3B,UAAU,EAAE,MAAM,CAAC,WAAW,CAC1B,CAAC,KAAK,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC;gBAC1C,IAAI;gBACJ,EAAC,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,CAAC,EAAC;aAChC,CAAC,CACL;SACJ;QACD,gBAAgB,EAAE,EAAC,IAAI,EAAE,QAAQ,EAAC;QAClC,kBAAkB,EAAE,EAAC,IAAI,EAAE,QAAQ,EAAC;QACpC,IAAI,EAAE,aAAa,CAAC,cAAc,CAAC;QACnC,KAAK,EAAE,aAAa,CAAC,eAAe,CAAC;QACrC,aAAa,EAAE;YACX,IAAI,EAAE,QAAQ;YACd,IAAI,EAAE,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,CAAC;SAC9B;QACD,QAAQ,EAAE,EAAC,IAAI,EAAE,SAAS,EAAC;KAC9B;CACJ,CAAC;AAEF,MAAM,CAAC,MAAM,WAAW,GAAG;IACvB,cAAc,EAAE,WAAW;CAC9B,CAAC","sourcesContent":["import {\n AnimatableProps,\n BlockBaseProps,\n BlockHeaderProps,\n containerSizesObject,\n} from '../../schema/validators/common';\nimport {AnalyticsEventSchema} from '../../schema/validators/event';\nimport {filteredArray} from '../../schema/validators/utils';\n\nexport const FilterTagProps = {\n type: 'object',\n additionalProperties: false,\n required: ['id', 'label'],\n properties: {\n id: {\n type: 'string',\n },\n label: {\n type: 'string',\n },\n analyticsEvent: AnalyticsEventSchema,\n collapsible: {type: 'boolean'},\n },\n};\n\nexport const FilterItemProps = {\n additionalProperties: false,\n required: ['tags', 'card'],\n properties: {\n tags: {\n type: 'array',\n items: {\n type: 'string',\n },\n },\n card: {$ref: 'self#/definitions/cards'},\n },\n};\n\nexport const FilterProps = {\n additionalProperties: false,\n required: ['tags', 'items'],\n properties: {\n ...BlockBaseProps,\n ...AnimatableProps,\n ...BlockHeaderProps,\n allTag: {\n oneOf: [\n {\n type: 'boolean',\n optionName: 'auto',\n },\n {\n type: 'string',\n optionName: 'cutom',\n },\n {\n ...FilterTagProps,\n },\n ],\n },\n colSizes: containerSizesObject,\n visibleRowsCount: {\n type: 'object',\n additionalProperties: false,\n properties: Object.fromEntries(\n ['all', 'sm', 'md', 'lg', 'xl'].map((size) => [\n size,\n {type: 'integer', minimum: 1},\n ]),\n ),\n },\n expandButtonText: {type: 'string'},\n collapseButtonText: {type: 'string'},\n tags: filteredArray(FilterTagProps),\n items: filteredArray(FilterItemProps),\n tagButtonSize: {\n type: 'string',\n enum: ['s', 'm', 'l', 'xl'],\n },\n centered: {type: 'boolean'},\n },\n};\n\nexport const FilterBlock = {\n 'filter-block': FilterProps,\n};\n"]}
@@ -72,15 +72,16 @@ unpredictable css rules order in build */
72
72
  .pc-footer-block__links-floor-list_wrap {
73
73
  flex-wrap: wrap;
74
74
  }
75
- .pc-footer-block__links-floor-list a {
75
+ .pc-footer-block.pc-footer-block .pc-footer-block__links-floor-list a {
76
76
  display: inline-block;
77
77
  text-decoration: none;
78
78
  color: var(--g-color-text-primary);
79
79
  }
80
- .pc-footer-block__links-floor-list a:hover {
80
+ .pc-footer-block.pc-footer-block .pc-footer-block__links-floor-list a:hover {
81
81
  color: var(--g-color-text-secondary);
82
82
  background-color: transparent;
83
83
  }
84
+
84
85
  .pc-footer-block__links-floor-inner_centered .pc-footer-block__links-floor-list_wrap {
85
86
  justify-content: center;
86
87
  }
@@ -12,7 +12,6 @@ unpredictable css rules order in build */
12
12
  .pc-fullscreen-image__modal-content {
13
13
  position: relative;
14
14
  border-radius: var(--pc-border-radius);
15
- width: 100%;
16
15
  }
17
16
  .pc-fullscreen-image__modal-content-wrapper {
18
17
  width: 100%;
@@ -27,6 +26,7 @@ unpredictable css rules order in build */
27
26
  justify-content: center;
28
27
  }
29
28
  .pc-fullscreen-image__modal_with-slider .pc-fullscreen-image__modal-content {
29
+ width: 100%;
30
30
  background-color: transparent;
31
31
  }
32
32
  .pc-fullscreen-image__modal_with-slider .pc-fullscreen-image__modal-content:hover .pc-fullscreen-image__expand-icon-wrapper, .pc-fullscreen-image__modal_with-slider .pc-fullscreen-image__modal-content:hover .pc-fullscreen-image__close-icon-wrapper {
@@ -19,7 +19,7 @@ export declare const blockMap: {
19
19
  "content-layout-block": (props: import("./models/index.js").ContentLayoutBlockProps) => import("react/jsx-runtime").JSX.Element;
20
20
  "share-block": ({ items, title }: import("./models/index.js").ShareBlockProps) => import("react/jsx-runtime").JSX.Element;
21
21
  "map-block": ({ map, border, disableShadow, ...props }: import("./models/index.js").MapBlockProps) => import("react/jsx-runtime").JSX.Element;
22
- "filter-block": ({ title, description, tags, tagButtonSize, allTag, items, colSizes, centered, animated, }: import("./models/index.js").FilterBlockProps) => import("react/jsx-runtime").JSX.Element;
22
+ "filter-block": ({ title, description, tags, tagButtonSize, allTag, items, colSizes, visibleRowsCount, expandButtonText, collapseButtonText, centered, animated, }: import("./models/index.js").FilterBlockProps) => import("react/jsx-runtime").JSX.Element;
23
23
  "form-block": (props: import("./models/index.js").FormBlockProps) => import("react/jsx-runtime").JSX.Element | null;
24
24
  "slider-block": ({ animated, title, description, type, anchorId, arrows, adaptive, autoplay: autoplayMs, dots, initialSlide, className, dotsClassName, disclaimer, children, blockClassName, arrowSize, slidesToShow, onSlideChange, onSlideChangeTransitionStart, onSlideChangeTransitionEnd, onActiveIndexChange, onBreakpoint, }: React.PropsWithChildren<import("./blocks/Slider/Slider.js").SliderProps>) => import("react/jsx-runtime").JSX.Element;
25
25
  };
@@ -66,12 +66,13 @@ unpredictable css rules order in build */
66
66
  font-family: var(--g-font-family-sans);
67
67
  color: var(--g-color-text-primary);
68
68
  }
69
- .yfm_constructor code,
70
- .yfm_constructor kbd,
71
- .yfm_constructor pre {
69
+ .yfm_constructor.yfm_constructor code,
70
+ .yfm_constructor.yfm_constructor kbd,
71
+ .yfm_constructor.yfm_constructor pre {
72
72
  font-family: var(--g-font-family-monospace);
73
73
  color: var(--g-color-text-primary);
74
74
  }
75
+
75
76
  .yfm_constructor.yfm_constructor h1,
76
77
  .yfm_constructor.yfm_constructor h2,
77
78
  .yfm_constructor.yfm_constructor h3,
@@ -150,13 +151,13 @@ unpredictable css rules order in build */
150
151
  .yfm_constructor a:focus:not(:focus-visible) {
151
152
  box-shadow: none;
152
153
  }
153
- .yfm_constructor table {
154
+ .yfm_constructor.yfm_constructor table {
154
155
  color: var(--g-color-text-primary);
155
156
  border: 1px solid var(--g-color-line-generic);
156
157
  background: var(--g-color-base-background);
157
158
  }
158
- .yfm_constructor thead,
159
- .yfm_constructor table tr:nth-child(2n) {
159
+ .yfm_constructor.yfm_constructor thead,
160
+ .yfm_constructor.yfm_constructor table tr:nth-child(2n) {
160
161
  background-color: var(--g-color-base-generic);
161
162
  }
162
163
 
@@ -301,6 +301,7 @@ export interface CardLayoutBlockProps extends Childable, Animatable, LoadableChi
301
301
  }>;
302
302
  }
303
303
  export type FilterTag = {
304
+ collapsible?: boolean;
304
305
  id: string;
305
306
  label: string;
306
307
  analyticsEvent?: AnalyticsEventsProp;
@@ -310,6 +311,9 @@ export type FilterItem = {
310
311
  card: SubBlockModels;
311
312
  };
312
313
  export interface FilterBlockProps extends Animatable {
314
+ visibleRowsCount?: Partial<Record<GridColumnSize, number>>;
315
+ expandButtonText?: string;
316
+ collapseButtonText?: string;
313
317
  tags: FilterTag[];
314
318
  items: FilterItem[];
315
319
  title?: TitleItemProps | string;