@elementor/editor-controls 3.33.0-98 → 3.34.2

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 (94) hide show
  1. package/dist/index.d.mts +264 -74
  2. package/dist/index.d.ts +264 -74
  3. package/dist/index.js +2541 -1861
  4. package/dist/index.js.map +1 -1
  5. package/dist/index.mjs +2344 -1660
  6. package/dist/index.mjs.map +1 -1
  7. package/package.json +31 -17
  8. package/src/bound-prop-context/prop-context.tsx +8 -1
  9. package/src/bound-prop-context/use-bound-prop.ts +19 -5
  10. package/src/components/autocomplete.tsx +34 -3
  11. package/src/components/conditional-control-infotip.tsx +64 -0
  12. package/src/components/{unstable-repeater → control-repeater}/actions/disable-item-action.tsx +2 -2
  13. package/src/components/{unstable-repeater → control-repeater}/actions/duplicate-item-action.tsx +10 -4
  14. package/src/components/{unstable-repeater → control-repeater}/actions/remove-item-action.tsx +2 -2
  15. package/src/components/control-repeater/context/item-context.tsx +8 -0
  16. package/src/components/{unstable-repeater → control-repeater}/context/repeater-context.tsx +24 -15
  17. package/src/components/control-repeater/control-repeater.tsx +29 -0
  18. package/src/components/{unstable-repeater → control-repeater}/index.ts +1 -2
  19. package/src/components/{unstable-repeater → control-repeater}/items/edit-item-popover.tsx +6 -20
  20. package/src/components/control-repeater/items/item.tsx +75 -0
  21. package/src/components/{unstable-repeater → control-repeater}/items/items-container.tsx +8 -13
  22. package/src/components/{unstable-repeater → control-repeater}/locations.ts +0 -4
  23. package/src/components/{unstable-repeater → control-repeater}/types.ts +1 -2
  24. package/src/components/control-toggle-button-group.tsx +79 -69
  25. package/src/components/enable-unfiltered-modal.tsx +1 -26
  26. package/src/components/icon-buttons/clear-icon-button.tsx +23 -0
  27. package/src/components/inline-editor-toolbar.tsx +137 -0
  28. package/src/components/inline-editor.tsx +111 -0
  29. package/src/components/item-selector.tsx +10 -4
  30. package/src/components/{unstable-repeater/header/header.tsx → repeater/repeater-header.tsx} +4 -12
  31. package/src/components/repeater/repeater-popover.tsx +19 -0
  32. package/src/components/repeater/repeater-tag.tsx +16 -0
  33. package/src/components/repeater/repeater.tsx +405 -0
  34. package/src/components/{sortable.tsx → repeater/sortable.tsx} +1 -1
  35. package/src/components/size-control/size-input.tsx +20 -14
  36. package/src/components/size-control/text-field-inner-selection.tsx +15 -2
  37. package/src/control-adornments/control-adornments-context.tsx +5 -4
  38. package/src/control-replacements.tsx +3 -43
  39. package/src/controls/background-control/background-control.tsx +43 -12
  40. package/src/controls/background-control/background-gradient-color-control.tsx +5 -8
  41. package/src/controls/background-control/background-overlay/background-image-overlay/background-image-overlay-position.tsx +18 -13
  42. package/src/controls/background-control/background-overlay/background-overlay-repeater-control.tsx +25 -16
  43. package/src/controls/box-shadow-repeater-control.tsx +38 -21
  44. package/src/controls/color-control.tsx +3 -1
  45. package/src/controls/date-time-control.tsx +108 -0
  46. package/src/controls/filter-control/drop-shadow/drop-shadow-item-content.tsx +1 -0
  47. package/src/controls/filter-control/drop-shadow/drop-shadow-item-label.tsx +10 -6
  48. package/src/controls/filter-control/filter-content.tsx +1 -1
  49. package/src/controls/filter-control/filter-repeater-control.tsx +24 -21
  50. package/src/controls/filter-control/single-size/single-size-item-content.tsx +1 -1
  51. package/src/controls/filter-control/single-size/single-size-item-label.tsx +2 -1
  52. package/src/controls/font-family-control/font-family-control.tsx +66 -55
  53. package/src/controls/html-tag-control.tsx +90 -0
  54. package/src/controls/image-media-control.tsx +2 -2
  55. package/src/controls/inline-editing-control.tsx +18 -0
  56. package/src/controls/key-value-control.tsx +8 -2
  57. package/src/controls/link-control.tsx +23 -123
  58. package/src/controls/linked-dimensions-control.tsx +71 -33
  59. package/src/controls/query-control.tsx +168 -0
  60. package/src/controls/repeatable-control.tsx +62 -27
  61. package/src/controls/select-control-wrapper.tsx +57 -0
  62. package/src/controls/select-control.tsx +9 -5
  63. package/src/controls/selection-size-control.tsx +13 -2
  64. package/src/controls/size-control.tsx +32 -59
  65. package/src/controls/svg-media-control.tsx +33 -10
  66. package/src/controls/text-area-control.tsx +5 -1
  67. package/src/controls/text-control.tsx +5 -0
  68. package/src/controls/toggle-control.tsx +11 -2
  69. package/src/controls/transform-control/functions/axis-row.tsx +1 -0
  70. package/src/controls/transform-control/transform-icon.tsx +2 -2
  71. package/src/controls/transform-control/transform-label.tsx +15 -32
  72. package/src/controls/transform-control/transform-repeater-control.tsx +42 -36
  73. package/src/controls/transform-control/{transform-base-control.tsx → transform-settings-control.tsx} +2 -2
  74. package/src/controls/transform-control/use-transform-tabs-history.tsx +1 -1
  75. package/src/controls/transition-control/data.ts +16 -1
  76. package/src/controls/transition-control/trainsition-events.ts +2 -2
  77. package/src/controls/transition-control/transition-repeater-control.tsx +137 -13
  78. package/src/controls/transition-control/transition-selector.tsx +37 -14
  79. package/src/controls/url-control.tsx +21 -16
  80. package/src/hooks/use-filtered-items-list.ts +3 -2
  81. package/src/hooks/use-repeatable-control-context.ts +3 -0
  82. package/src/hooks/use-sync-external-state.tsx +0 -1
  83. package/src/index.ts +21 -5
  84. package/src/utils/convert-toggle-options-to-atomic.tsx +33 -0
  85. package/src/utils/escape-html-attr.ts +11 -0
  86. package/src/components/css-code-editor/css-editor.styles.ts +0 -52
  87. package/src/components/css-code-editor/css-editor.tsx +0 -142
  88. package/src/components/css-code-editor/css-validation.ts +0 -75
  89. package/src/components/css-code-editor/resize-handle.tsx +0 -55
  90. package/src/components/css-code-editor/visual-content-change-protection.ts +0 -69
  91. package/src/components/repeater.tsx +0 -343
  92. package/src/components/unstable-repeater/items/item.tsx +0 -77
  93. package/src/components/unstable-repeater/unstable-repeater.tsx +0 -26
  94. /package/src/components/{unstable-repeater → control-repeater}/actions/tooltip-add-item-action.tsx +0 -0
@@ -1,17 +1,30 @@
1
1
  import * as React from 'react';
2
- import { useEffect, useState } from 'react';
3
- import { selectionSizePropTypeUtil } from '@elementor/editor-props';
2
+ import { useEffect, useMemo, useState } from 'react';
3
+ import {
4
+ createArrayPropUtils,
5
+ type KeyValuePropValue,
6
+ selectionSizePropTypeUtil,
7
+ type SelectionSizePropValue,
8
+ } from '@elementor/editor-props';
4
9
  import { type StyleDefinitionState } from '@elementor/editor-styles';
5
10
  import { InfoCircleFilledIcon } from '@elementor/icons';
6
11
  import { Alert, AlertTitle, Box, Typography } from '@elementor/ui';
7
12
  import { __ } from '@wordpress/i18n';
8
13
 
14
+ import { useBoundProp } from '../../bound-prop-context';
15
+ import { type Item, type RepeatablePropValue } from '../../components/control-repeater/types';
9
16
  import { createControl } from '../../create-control';
10
17
  import { RepeatableControl } from '../repeatable-control';
11
18
  import { SelectionSizeControl } from '../selection-size-control';
12
- import { initialTransitionValue, transitionProperties } from './data';
19
+ import {
20
+ initialTransitionValue,
21
+ type TransitionItem,
22
+ transitionProperties,
23
+ type TransitionProperty,
24
+ type TransitionValue,
25
+ } from './data';
13
26
  import { subscribeToTransitionEvent } from './trainsition-events';
14
- import { TransitionSelector } from './transition-selector';
27
+ import { getTransitionPropertyByValue, TransitionSelector } from './transition-selector';
15
28
 
16
29
  const DURATION_CONFIG = {
17
30
  variant: 'time',
@@ -19,9 +32,34 @@ const DURATION_CONFIG = {
19
32
  defaultUnit: 'ms',
20
33
  };
21
34
 
35
+ const childArrayPropTypeUtil = createArrayPropUtils(
36
+ selectionSizePropTypeUtil.key,
37
+ selectionSizePropTypeUtil.schema,
38
+ 'transition'
39
+ );
40
+
41
+ subscribeToTransitionEvent();
42
+
43
+ const areAllPropertiesUsed = ( value: SelectionSizePropValue[] = [] ) => {
44
+ return value?.length
45
+ ? transitionProperties.every( ( category ) => {
46
+ return category.properties.every( ( property ) => {
47
+ return (
48
+ property.isDisabled ||
49
+ !! value?.find( ( item ) => {
50
+ return (
51
+ ( item.value?.selection?.value as KeyValuePropValue )?.value?.value === property.value
52
+ );
53
+ } )
54
+ );
55
+ } );
56
+ } )
57
+ : false;
58
+ };
59
+
22
60
  // this config needs to be loaded at runtime/render since it's the transitionProperties object will be mutated by the pro plugin.
23
61
  // See: https://elementor.atlassian.net/browse/ED-20285
24
- const getSelectionSizeProps = ( recentlyUsedList: string[] ) => {
62
+ const getSelectionSizeProps = ( recentlyUsedList: string[], disabledItems?: string[] ) => {
25
63
  return {
26
64
  selectionLabel: __( 'Type', 'elementor' ),
27
65
  sizeLabel: __( 'Duration', 'elementor' ),
@@ -29,8 +67,10 @@ const getSelectionSizeProps = ( recentlyUsedList: string[] ) => {
29
67
  component: TransitionSelector,
30
68
  props: {
31
69
  recentlyUsedList,
70
+ disabledItems,
32
71
  },
33
72
  },
73
+ isRepeaterControl: true,
34
74
  sizeConfigMap: {
35
75
  ...transitionProperties.reduce(
36
76
  ( acc, category ) => {
@@ -45,13 +85,69 @@ const getSelectionSizeProps = ( recentlyUsedList: string[] ) => {
45
85
  };
46
86
  };
47
87
 
48
- function getChildControlConfig( recentlyUsedList: string[] ) {
88
+ const isItemDisabled = ( item: TransitionItem[ 'value' ] ) => {
89
+ const property = getTransitionPropertyByValue( item.value.selection.value?.value );
90
+
91
+ return ! property ? false : !! property.isDisabled;
92
+ };
93
+
94
+ const getChildControlConfig = ( recentlyUsedList: string[], disabledItems?: string[] ) => {
49
95
  return {
50
96
  propTypeUtil: selectionSizePropTypeUtil,
51
97
  component: SelectionSizeControl as unknown as React.ComponentType< Record< string, unknown > >,
52
- props: getSelectionSizeProps( recentlyUsedList ),
98
+ props: getSelectionSizeProps( recentlyUsedList, disabledItems ),
99
+ isItemDisabled: isItemDisabled as ( item: Item< RepeatablePropValue > ) => boolean,
53
100
  };
54
- }
101
+ };
102
+
103
+ const isPropertyUsed = ( value: SelectionSizePropValue[], property: TransitionProperty ) => {
104
+ return ( value ?? [] ).some( ( item ) => {
105
+ return ( item?.value?.selection?.value as KeyValuePropValue )?.value?.value === property.value;
106
+ } );
107
+ };
108
+
109
+ const getDisabledItemLabels = ( values: SelectionSizePropValue[] = [] ) => {
110
+ const disabledLabels: string[] = ( values || [] ).map(
111
+ ( item ) => ( item.value?.selection as KeyValuePropValue )?.value?.key?.value
112
+ );
113
+
114
+ transitionProperties.forEach( ( category ) => {
115
+ const disabledProperties = category.properties
116
+ .filter( ( property ) => property.isDisabled && ! disabledLabels.includes( property.label ) )
117
+ .map( ( property ) => property.label );
118
+
119
+ disabledLabels.push( ...disabledProperties );
120
+ } );
121
+
122
+ return disabledLabels;
123
+ };
124
+
125
+ const getInitialValue = ( values: SelectionSizePropValue[] = [] ): TransitionValue => {
126
+ if ( ! values?.length ) {
127
+ return initialTransitionValue;
128
+ }
129
+
130
+ for ( const category of transitionProperties ) {
131
+ for ( const property of category.properties ) {
132
+ if ( isPropertyUsed( values, property ) ) {
133
+ continue;
134
+ }
135
+
136
+ return {
137
+ ...initialTransitionValue,
138
+ selection: {
139
+ $$type: 'key-value',
140
+ value: {
141
+ key: { value: property.label, $$type: 'string' },
142
+ value: { value: property.value, $$type: 'string' },
143
+ },
144
+ },
145
+ };
146
+ }
147
+ }
148
+
149
+ return initialTransitionValue;
150
+ };
55
151
 
56
152
  const disableAddItemTooltipContent = (
57
153
  <Alert
@@ -71,8 +167,6 @@ const disableAddItemTooltipContent = (
71
167
  </Alert>
72
168
  );
73
169
 
74
- subscribeToTransitionEvent();
75
-
76
170
  export const TransitionRepeaterControl = createControl(
77
171
  ( {
78
172
  recentlyUsedListGetter,
@@ -84,10 +178,40 @@ export const TransitionRepeaterControl = createControl(
84
178
  const currentStyleIsNormal = currentStyleState === null;
85
179
  const [ recentlyUsedList, setRecentlyUsedList ] = useState< string[] >( [] );
86
180
 
181
+ const { value, setValue } = useBoundProp( childArrayPropTypeUtil );
182
+ const disabledItems = useMemo( () => getDisabledItemLabels( value ), [ value ] );
183
+
184
+ const allowedTransitionSet = useMemo( () => {
185
+ const set = new Set< string >();
186
+ transitionProperties.forEach( ( category ) => {
187
+ category.properties.forEach( ( prop ) => set.add( prop.value ) );
188
+ } );
189
+ return set;
190
+ }, [] );
191
+
192
+ useEffect( () => {
193
+ if ( ! value || value.length === 0 ) {
194
+ return;
195
+ }
196
+
197
+ const sanitized = value.filter( ( item ) => {
198
+ const selectionValue = ( item?.value?.selection?.value as KeyValuePropValue )?.value?.value ?? '';
199
+ return allowedTransitionSet.has( selectionValue );
200
+ } );
201
+
202
+ if ( sanitized.length !== value.length ) {
203
+ setValue( sanitized );
204
+ }
205
+ // eslint-disable-next-line react-hooks/exhaustive-deps
206
+ }, [ allowedTransitionSet ] );
207
+
87
208
  useEffect( () => {
88
209
  recentlyUsedListGetter().then( setRecentlyUsedList );
89
210
  }, [ recentlyUsedListGetter ] );
90
211
 
212
+ const allPropertiesUsed = useMemo( () => areAllPropertiesUsed( value ), [ value ] );
213
+ const isAddItemDisabled = ! currentStyleIsNormal || allPropertiesUsed;
214
+
91
215
  return (
92
216
  <RepeatableControl
93
217
  label={ __( 'Transitions', 'elementor' ) }
@@ -96,11 +220,11 @@ export const TransitionRepeaterControl = createControl(
96
220
  placeholder={ __( 'Empty Transition', 'elementor' ) }
97
221
  showDuplicate={ false }
98
222
  showToggle={ true }
99
- initialValues={ initialTransitionValue }
100
- childControlConfig={ getChildControlConfig( recentlyUsedList ) }
223
+ initialValues={ getInitialValue( value ) }
224
+ childControlConfig={ getChildControlConfig( recentlyUsedList, disabledItems ) }
101
225
  propKey="transition"
102
226
  addItemTooltipProps={ {
103
- disabled: ! currentStyleIsNormal,
227
+ disabled: isAddItemDisabled,
104
228
  enableTooltip: ! currentStyleIsNormal,
105
229
  tooltipContent: disableAddItemTooltipContent,
106
230
  } }
@@ -1,12 +1,13 @@
1
1
  import * as React from 'react';
2
2
  import { useRef } from 'react';
3
- import { keyValuePropTypeUtil } from '@elementor/editor-props';
3
+ import { keyValuePropTypeUtil, type KeyValuePropValue, type StringPropValue } from '@elementor/editor-props';
4
4
  import { ChevronDownIcon, VariationsIcon } from '@elementor/icons';
5
5
  import { bindPopover, bindTrigger, Box, Popover, UnstableTag, usePopupState } from '@elementor/ui';
6
6
  import { __ } from '@wordpress/i18n';
7
7
 
8
8
  import { useBoundProp } from '../../bound-prop-context';
9
9
  import { ItemSelector } from '../../components/item-selector';
10
+ import ControlActions from '../../control-actions/control-actions';
10
11
  import { transitionProperties, transitionsItemsList } from './data';
11
12
 
12
13
  const toTransitionSelectorValue = ( label: string ) => {
@@ -23,16 +24,35 @@ const toTransitionSelectorValue = ( label: string ) => {
23
24
  return null;
24
25
  };
25
26
 
26
- const findByValue = ( value: string ) => {
27
+ export function getTransitionPropertyByValue( item?: StringPropValue | null ) {
28
+ if ( ! item?.value ) {
29
+ return null;
30
+ }
31
+
27
32
  for ( const category of transitionProperties ) {
28
- const property = category.properties.find( ( prop ) => prop.value === value );
29
- if ( property ) {
30
- return property.label;
33
+ for ( const property of category.properties ) {
34
+ if ( property.value === item.value ) {
35
+ return property;
36
+ }
31
37
  }
32
38
  }
39
+
40
+ return null;
41
+ }
42
+
43
+ const includeCurrentValueInOptions = ( value: KeyValuePropValue[ 'value' ], disabledItems: string[] ) => {
44
+ return disabledItems.filter( ( item ) => {
45
+ return item !== value.key.value;
46
+ } );
33
47
  };
34
48
 
35
- export const TransitionSelector = ( { recentlyUsedList = [] }: { recentlyUsedList: string[] } ) => {
49
+ export const TransitionSelector = ( {
50
+ recentlyUsedList = [],
51
+ disabledItems = [],
52
+ }: {
53
+ recentlyUsedList: string[];
54
+ disabledItems?: string[];
55
+ } ) => {
36
56
  const { value, setValue } = useBoundProp( keyValuePropTypeUtil );
37
57
  const {
38
58
  key: { value: transitionLabel },
@@ -42,7 +62,7 @@ export const TransitionSelector = ( { recentlyUsedList = [] }: { recentlyUsedLis
42
62
 
43
63
  const getItemList = () => {
44
64
  const recentItems = recentlyUsedList
45
- .map( ( item ) => findByValue( item ) )
65
+ .map( ( item ) => getTransitionPropertyByValue( { value: item, $$type: 'string' } )?.label )
46
66
  .filter( ( item ) => !! item ) as string[];
47
67
  const filteredItems = transitionsItemsList.map( ( category ) => {
48
68
  return {
@@ -89,13 +109,15 @@ export const TransitionSelector = ( { recentlyUsedList = [] }: { recentlyUsedLis
89
109
 
90
110
  return (
91
111
  <Box ref={ defaultRef }>
92
- <UnstableTag
93
- variant="outlined"
94
- label={ transitionLabel }
95
- endIcon={ <ChevronDownIcon fontSize="tiny" /> }
96
- { ...bindTrigger( popoverState ) }
97
- fullWidth
98
- />
112
+ <ControlActions>
113
+ <UnstableTag
114
+ variant="outlined"
115
+ label={ transitionLabel }
116
+ endIcon={ <ChevronDownIcon fontSize="tiny" /> }
117
+ { ...bindTrigger( popoverState ) }
118
+ fullWidth
119
+ />
120
+ </ControlActions>
99
121
  <Popover
100
122
  disablePortal
101
123
  disableScrollLock
@@ -113,6 +135,7 @@ export const TransitionSelector = ( { recentlyUsedList = [] }: { recentlyUsedLis
113
135
  sectionWidth={ 268 }
114
136
  title={ __( 'Transition Property', 'elementor' ) }
115
137
  icon={ VariationsIcon as React.ElementType< { fontSize: string } > }
138
+ disabledItems={ includeCurrentValueInOptions( value, disabledItems ) }
116
139
  />
117
140
  </Popover>
118
141
  </Box>
@@ -6,20 +6,25 @@ import { useBoundProp } from '../bound-prop-context';
6
6
  import ControlActions from '../control-actions/control-actions';
7
7
  import { createControl } from '../create-control';
8
8
 
9
- export const UrlControl = createControl( ( { placeholder }: { placeholder?: string } ) => {
10
- const { value, setValue, disabled } = useBoundProp( urlPropTypeUtil );
11
- const handleChange = ( event: React.ChangeEvent< HTMLInputElement > ) => setValue( event.target.value );
9
+ export const UrlControl = createControl(
10
+ ( { placeholder, ariaLabel }: { placeholder?: string; ariaLabel?: string } ) => {
11
+ const { value, setValue, disabled } = useBoundProp( urlPropTypeUtil );
12
+ const handleChange = ( event: React.ChangeEvent< HTMLInputElement > ) => setValue( event.target.value );
12
13
 
13
- return (
14
- <ControlActions>
15
- <TextField
16
- size="tiny"
17
- fullWidth
18
- value={ value ?? '' }
19
- disabled={ disabled }
20
- onChange={ handleChange }
21
- placeholder={ placeholder }
22
- />
23
- </ControlActions>
24
- );
25
- } );
14
+ return (
15
+ <ControlActions>
16
+ <TextField
17
+ size="tiny"
18
+ fullWidth
19
+ value={ value ?? '' }
20
+ disabled={ disabled }
21
+ onChange={ handleChange }
22
+ placeholder={ placeholder }
23
+ inputProps={ {
24
+ ...( ariaLabel ? { 'aria-label': ariaLabel } : {} ),
25
+ } }
26
+ />
27
+ </ControlActions>
28
+ );
29
+ }
30
+ );
@@ -3,9 +3,10 @@ import { type Category } from '../components/item-selector';
3
3
  export type SelectableItem = {
4
4
  type: 'item' | 'category';
5
5
  value: string;
6
+ disabled?: boolean;
6
7
  };
7
8
 
8
- export const useFilteredItemsList = ( itemsList: Category[], searchValue: string ) => {
9
+ export const useFilteredItemsList = ( itemsList: Category[], searchValue: string, disabledItems?: string[] ) => {
9
10
  return itemsList.reduce< SelectableItem[] >( ( acc, category ) => {
10
11
  const filteredItems = category.items.filter( ( item ) =>
11
12
  item.toLowerCase().includes( searchValue.toLowerCase() )
@@ -15,7 +16,7 @@ export const useFilteredItemsList = ( itemsList: Category[], searchValue: string
15
16
  acc.push( { type: 'category', value: category.label } );
16
17
 
17
18
  filteredItems.forEach( ( item ) => {
18
- acc.push( { type: 'item', value: item } );
19
+ acc.push( { type: 'item', value: item, disabled: disabledItems?.includes( item ) ?? false } );
19
20
  } );
20
21
  }
21
22
 
@@ -1,12 +1,15 @@
1
1
  import { createContext, useContext } from 'react';
2
2
  import { type PropTypeUtil } from '@elementor/editor-props';
3
3
 
4
+ import type { Item, RepeatablePropValue } from '../components/control-repeater/types';
5
+
4
6
  export type ChildControlConfig = {
5
7
  component: React.ComponentType;
6
8
  props?: Record< string, unknown >;
7
9
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
8
10
  propTypeUtil: PropTypeUtil< string, any >;
9
11
  label?: string;
12
+ isItemDisabled?: ( item: Item< RepeatablePropValue > ) => boolean;
10
13
  };
11
14
 
12
15
  type RepeatableControlContextType = ChildControlConfig & {
@@ -37,7 +37,6 @@ export const useSyncExternalState = < TValue, >( {
37
37
  useEffect( () => {
38
38
  setInternal( ( prevInternal ) => toInternal( external, prevInternal ) );
39
39
 
40
- // eslint-disable-next-line react-compiler/react-compiler
41
40
  // eslint-disable-next-line react-hooks/exhaustive-deps
42
41
  }, [ external ] );
43
42
 
package/src/index.ts CHANGED
@@ -7,6 +7,7 @@ export { StrokeControl } from './controls/stroke-control';
7
7
  export { BoxShadowRepeaterControl } from './controls/box-shadow-repeater-control';
8
8
  export { FilterRepeaterControl } from './controls/filter-control/filter-repeater-control';
9
9
  export { SelectControl } from './controls/select-control';
10
+ export { SelectControlWrapper } from './controls/select-control-wrapper';
10
11
  export { ColorControl } from './controls/color-control';
11
12
  export { ToggleControl } from './controls/toggle-control';
12
13
  export { NumberControl } from './controls/number-control';
@@ -16,6 +17,8 @@ export { FontFamilyControl } from './controls/font-family-control/font-family-co
16
17
  export { ItemSelector } from './components/item-selector';
17
18
  export { UrlControl } from './controls/url-control';
18
19
  export { LinkControl } from './controls/link-control';
20
+ export { HtmlTagControl } from './controls/html-tag-control';
21
+ export { QueryControl } from './controls/query-control';
19
22
  export { GapControl } from './controls/gap-control';
20
23
  export { AspectRatioControl } from './controls/aspect-ratio-control';
21
24
  export { SvgMediaControl } from './controls/svg-media-control';
@@ -25,24 +28,38 @@ export { RepeatableControl } from './controls/repeatable-control';
25
28
  export { KeyValueControl } from './controls/key-value-control';
26
29
  export { PositionControl } from './controls/position-control';
27
30
  export { TransformRepeaterControl } from './controls/transform-control/transform-repeater-control';
28
- export { TransformBaseControl } from './controls/transform-control/transform-base-control';
31
+ export { TransformSettingsControl } from './controls/transform-control/transform-settings-control';
29
32
  export { TransitionRepeaterControl } from './controls/transition-control/transition-repeater-control';
30
33
  export { PopoverContent } from './components/popover-content';
31
34
  export { enqueueFont } from './controls/font-family-control/enqueue-font';
32
35
  export { transitionProperties, transitionsItemsList } from './controls/transition-control/data';
36
+ export { DateTimeControl } from './controls/date-time-control';
37
+ export { InlineEditingControl } from './controls/inline-editing-control';
38
+ export { InlineEditor } from './components/inline-editor';
39
+ export { InlineEditorToolbar } from './components/inline-editor-toolbar';
33
40
 
34
41
  // components
35
42
  export { ControlFormLabel } from './components/control-form-label';
36
43
  export { ControlToggleButtonGroup } from './components/control-toggle-button-group';
37
- export { CssEditor } from './components/css-code-editor/css-editor';
44
+ export { ToggleButtonGroupUi } from './components/control-toggle-button-group';
45
+ export { ClearIconButton } from './components/icon-buttons/clear-icon-button';
46
+ export {
47
+ Repeater,
48
+ type SetRepeaterValuesMeta,
49
+ type ItemsActionPayload,
50
+ type RepeaterItem,
51
+ } from './components/repeater/repeater';
52
+ export { FloatingActionsBar } from './components/floating-bar';
53
+ export { PopoverGridContainer } from './components/popover-grid-container';
38
54
 
39
55
  // types
40
56
  export type { ControlComponent } from './create-control';
41
57
  export type { ToggleButtonGroupItem } from './components/control-toggle-button-group';
42
58
  export type { EqualUnequalItems } from './controls/equal-unequal-sizes-control';
43
59
  export type { ControlActionsItems } from './control-actions/control-actions-context';
60
+ export type { AdornmentComponent } from './control-adornments/control-adornments-context';
44
61
  export type { PropProviderProps } from './bound-prop-context';
45
- export type { SetValue } from './bound-prop-context/prop-context';
62
+ export type { SetValue, SetValueMeta } from './bound-prop-context/prop-context';
46
63
  export type { ExtendedOption, Unit, LengthUnit, AngleUnit, TimeUnit } from './utils/size-control';
47
64
  export type { ToggleControlProps } from './controls/toggle-control';
48
65
  export type { FontCategory } from './controls/font-family-control/font-family-control';
@@ -59,9 +76,8 @@ export { createControl } from './create-control';
59
76
  export {
60
77
  injectIntoRepeaterItemIcon,
61
78
  injectIntoRepeaterItemLabel,
62
- injectIntoRepeaterHeaderActions,
63
79
  injectIntoRepeaterItemActions,
64
- } from './components/unstable-repeater/locations';
80
+ } from './components/control-repeater/locations';
65
81
 
66
82
  // hooks
67
83
  export { useSyncExternalState } from './hooks/use-sync-external-state';
@@ -0,0 +1,33 @@
1
+ import * as React from 'react';
2
+ import type { ToggleButtonGroupItem } from '@elementor/editor-controls';
3
+ import * as Icons from '@elementor/icons';
4
+
5
+ export type DynamicToggleOption = {
6
+ value: string;
7
+ label: string;
8
+ icon?: string;
9
+ showTooltip?: boolean;
10
+ exclusive?: boolean;
11
+ };
12
+
13
+ export const convertToggleOptionsToAtomic = (
14
+ options: DynamicToggleOption[]
15
+ ): Array< ToggleButtonGroupItem< string > & { exclusive?: boolean } > => {
16
+ return options.map( ( option ) => {
17
+ const iconName = option.icon;
18
+ const IconComponent = Icons[ iconName as keyof typeof Icons ];
19
+
20
+ return {
21
+ value: option.value,
22
+ label: option.label,
23
+ renderContent: ( { size } ) => {
24
+ if ( IconComponent ) {
25
+ return <IconComponent fontSize={ size } />;
26
+ }
27
+ return option.label;
28
+ },
29
+ showTooltip: option.showTooltip,
30
+ exclusive: option.exclusive,
31
+ };
32
+ } );
33
+ };
@@ -0,0 +1,11 @@
1
+ export const escapeHtmlAttr = ( value: string ): string => {
2
+ const specialChars: Record< string, string > = {
3
+ '&': '&amp;',
4
+ '<': '&lt;',
5
+ '>': '&gt;',
6
+ "'": '&#39;',
7
+ '"': '&quot;',
8
+ };
9
+
10
+ return value.replace( /[&<>'"]/g, ( char ) => specialChars[ char ] || char );
11
+ };
@@ -1,52 +0,0 @@
1
- import { Box, Button, styled } from '@elementor/ui';
2
-
3
- export const EditorWrapper = styled( Box )`
4
- border: 1px solid var( --e-a-border-color );
5
- border-radius: 8px;
6
- padding: 10px 12px;
7
- position: relative;
8
- height: 200px;
9
-
10
- .monaco-editor .suggest-widget {
11
- width: 220px !important;
12
- max-width: 220px !important;
13
- }
14
-
15
- .visual-content-dimmed {
16
- opacity: 0.6;
17
- color: #aaa !important;
18
- pointer-events: none;
19
- }
20
- `;
21
-
22
- export const ResizeHandle = styled( Button )`
23
- position: absolute;
24
- bottom: 0;
25
- left: 0;
26
- right: 0;
27
- height: 6px;
28
- cursor: ns-resize;
29
- background: transparent;
30
- border: none;
31
- padding: 0;
32
-
33
- &:hover {
34
- background: rgba( 0, 0, 0, 0.05 );
35
- }
36
-
37
- &:active {
38
- background: rgba( 0, 0, 0, 0.1 );
39
- }
40
-
41
- &::after {
42
- content: '';
43
- position: absolute;
44
- top: 50%;
45
- left: 50%;
46
- transform: translate( -50%, -50% );
47
- width: 30px;
48
- height: 2px;
49
- background: var( --e-a-border-color );
50
- border-radius: 1px;
51
- }
52
- `;