@elementor/editor-controls 0.30.1 → 0.32.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.
- package/CHANGELOG.md +33 -0
- package/dist/index.d.mts +9 -2
- package/dist/index.d.ts +9 -2
- package/dist/index.js +373 -236
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +303 -168
- package/dist/index.mjs.map +1 -1
- package/package.json +7 -6
- package/src/components/text-field-inner-selection.tsx +3 -0
- package/src/controls/aspect-ratio-control.tsx +121 -0
- package/src/controls/background-control/background-control.tsx +10 -1
- package/src/controls/background-control/background-overlay/background-overlay-repeater-control.tsx +6 -6
- package/src/controls/box-shadow-repeater-control.tsx +1 -15
- package/src/controls/color-control.tsx +34 -11
- package/src/controls/link-control.tsx +1 -1
- package/src/controls/size-control.tsx +31 -1
- package/src/controls/switch-control.tsx +20 -0
- package/src/index.ts +2 -0
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@elementor/editor-controls",
|
|
3
3
|
"description": "This package contains the controls model and utils for the Elementor editor",
|
|
4
|
-
"version": "0.
|
|
4
|
+
"version": "0.32.0",
|
|
5
5
|
"private": false,
|
|
6
6
|
"author": "Elementor Team",
|
|
7
7
|
"homepage": "https://elementor.com/",
|
|
@@ -40,17 +40,18 @@
|
|
|
40
40
|
"dev": "tsup --config=../../tsup.dev.ts"
|
|
41
41
|
},
|
|
42
42
|
"dependencies": {
|
|
43
|
-
"@elementor/editor-current-user": "0.
|
|
44
|
-
"@elementor/editor-elements": "0.8.
|
|
45
|
-
"@elementor/editor-props": "0.12.
|
|
46
|
-
"@elementor/editor-ui": "0.
|
|
43
|
+
"@elementor/editor-current-user": "0.5.0",
|
|
44
|
+
"@elementor/editor-elements": "0.8.4",
|
|
45
|
+
"@elementor/editor-props": "0.12.1",
|
|
46
|
+
"@elementor/editor-ui": "0.9.0",
|
|
47
|
+
"@elementor/editor-v1-adapters": "0.12.0",
|
|
47
48
|
"@elementor/env": "0.3.5",
|
|
48
49
|
"@elementor/http-client": "0.3.0",
|
|
49
50
|
"@elementor/icons": "1.40.1",
|
|
50
51
|
"@elementor/locations": "0.8.0",
|
|
51
52
|
"@elementor/query": "0.2.4",
|
|
52
53
|
"@elementor/session": "0.1.0",
|
|
53
|
-
"@elementor/ui": "1.34.
|
|
54
|
+
"@elementor/ui": "1.34.5",
|
|
54
55
|
"@elementor/utils": "0.4.0",
|
|
55
56
|
"@elementor/wp-media": "0.6.0",
|
|
56
57
|
"@tanstack/react-virtual": "3.13.3",
|
|
@@ -11,6 +11,7 @@ type TextFieldInnerSelectionProps = {
|
|
|
11
11
|
onChange: ( event: React.ChangeEvent< HTMLInputElement > ) => void;
|
|
12
12
|
onBlur?: ( event: React.FocusEvent< HTMLInputElement > ) => void;
|
|
13
13
|
onKeyDown?: ( event: React.KeyboardEvent< HTMLInputElement > ) => void;
|
|
14
|
+
onKeyUp?: ( event: React.KeyboardEvent< HTMLInputElement > ) => void;
|
|
14
15
|
endAdornment: React.ReactNode;
|
|
15
16
|
startAdornment?: React.ReactNode;
|
|
16
17
|
};
|
|
@@ -24,6 +25,7 @@ export const TextFieldInnerSelection = forwardRef(
|
|
|
24
25
|
onChange,
|
|
25
26
|
onBlur,
|
|
26
27
|
onKeyDown,
|
|
28
|
+
onKeyUp,
|
|
27
29
|
endAdornment,
|
|
28
30
|
startAdornment,
|
|
29
31
|
}: TextFieldInnerSelectionProps,
|
|
@@ -38,6 +40,7 @@ export const TextFieldInnerSelection = forwardRef(
|
|
|
38
40
|
value={ value }
|
|
39
41
|
onChange={ onChange }
|
|
40
42
|
onKeyDown={ onKeyDown }
|
|
43
|
+
onKeyUp={ onKeyUp }
|
|
41
44
|
onBlur={ onBlur }
|
|
42
45
|
placeholder={ placeholder }
|
|
43
46
|
InputProps={ {
|
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
import * as React from 'react';
|
|
2
|
+
import { useState } from 'react';
|
|
3
|
+
import { stringPropTypeUtil } from '@elementor/editor-props';
|
|
4
|
+
import { MenuListItem } from '@elementor/editor-ui';
|
|
5
|
+
import { Grid, Select, type SelectChangeEvent, Stack, TextField } from '@elementor/ui';
|
|
6
|
+
import { __ } from '@wordpress/i18n';
|
|
7
|
+
|
|
8
|
+
import { useBoundProp } from '../bound-prop-context';
|
|
9
|
+
import { ControlLabel } from '../components/control-label';
|
|
10
|
+
import { createControl } from '../create-control';
|
|
11
|
+
|
|
12
|
+
const RATIO_OPTIONS = [
|
|
13
|
+
{ label: __( 'Auto', 'elementor' ), value: 'auto' },
|
|
14
|
+
{ label: '1/1', value: '1/1' },
|
|
15
|
+
{ label: '4/3', value: '4/3' },
|
|
16
|
+
{ label: '3/4', value: '3/4' },
|
|
17
|
+
{ label: '16/9', value: '16/9' },
|
|
18
|
+
{ label: '9/16', value: '9/16' },
|
|
19
|
+
{ label: '3/2', value: '3/2' },
|
|
20
|
+
{ label: '2/3', value: '2/3' },
|
|
21
|
+
];
|
|
22
|
+
|
|
23
|
+
const CUSTOM_RATIO = 'custom';
|
|
24
|
+
|
|
25
|
+
export const AspectRatioControl = createControl( ( { label }: { label: string } ) => {
|
|
26
|
+
const { value: aspectRatioValue, setValue: setAspectRatioValue } = useBoundProp( stringPropTypeUtil );
|
|
27
|
+
|
|
28
|
+
const isCustomSelected =
|
|
29
|
+
aspectRatioValue && ! RATIO_OPTIONS.some( ( option ) => option.value === aspectRatioValue );
|
|
30
|
+
const [ initialWidth, initialHeight ] = isCustomSelected ? aspectRatioValue.split( '/' ) : [ '', '' ];
|
|
31
|
+
|
|
32
|
+
const [ isCustom, setIsCustom ] = useState( isCustomSelected );
|
|
33
|
+
const [ customWidth, setCustomWidth ] = useState< string >( initialWidth );
|
|
34
|
+
const [ customHeight, setCustomHeight ] = useState< string >( initialHeight );
|
|
35
|
+
const [ selectedValue, setSelectedValue ] = useState< string >(
|
|
36
|
+
isCustomSelected ? CUSTOM_RATIO : aspectRatioValue || ''
|
|
37
|
+
);
|
|
38
|
+
|
|
39
|
+
const handleSelectChange = ( event: SelectChangeEvent< string > ) => {
|
|
40
|
+
const newValue = event.target.value;
|
|
41
|
+
const isCustomRatio = newValue === CUSTOM_RATIO;
|
|
42
|
+
|
|
43
|
+
setIsCustom( isCustomRatio );
|
|
44
|
+
setSelectedValue( newValue );
|
|
45
|
+
|
|
46
|
+
if ( isCustomRatio ) {
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
setAspectRatioValue( newValue );
|
|
51
|
+
};
|
|
52
|
+
const handleCustomWidthChange = ( event: React.ChangeEvent< HTMLInputElement > ) => {
|
|
53
|
+
const newWidth = event.target.value;
|
|
54
|
+
setCustomWidth( newWidth );
|
|
55
|
+
|
|
56
|
+
if ( newWidth && customHeight ) {
|
|
57
|
+
setAspectRatioValue( `${ newWidth }/${ customHeight }` );
|
|
58
|
+
}
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
const handleCustomHeightChange = ( event: React.ChangeEvent< HTMLInputElement > ) => {
|
|
62
|
+
const newHeight = event.target.value;
|
|
63
|
+
setCustomHeight( newHeight );
|
|
64
|
+
|
|
65
|
+
if ( customWidth && newHeight ) {
|
|
66
|
+
setAspectRatioValue( `${ customWidth }/${ newHeight }` );
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
return (
|
|
71
|
+
<Stack direction="column" gap={ 2 }>
|
|
72
|
+
<Grid container gap={ 2 } alignItems="center" flexWrap="nowrap">
|
|
73
|
+
<Grid item xs={ 6 }>
|
|
74
|
+
<ControlLabel>{ label }</ControlLabel>
|
|
75
|
+
</Grid>
|
|
76
|
+
<Grid item xs={ 6 }>
|
|
77
|
+
<Select
|
|
78
|
+
sx={ { overflow: 'hidden' } }
|
|
79
|
+
displayEmpty
|
|
80
|
+
size="tiny"
|
|
81
|
+
value={ selectedValue }
|
|
82
|
+
onChange={ handleSelectChange }
|
|
83
|
+
fullWidth
|
|
84
|
+
>
|
|
85
|
+
{ [ ...RATIO_OPTIONS, { label: __( 'Custom', 'elementor' ), value: CUSTOM_RATIO } ].map(
|
|
86
|
+
( { label: optionLabel, ...props } ) => (
|
|
87
|
+
<MenuListItem key={ props.value } { ...props } value={ props.value ?? '' }>
|
|
88
|
+
{ optionLabel }
|
|
89
|
+
</MenuListItem>
|
|
90
|
+
)
|
|
91
|
+
) }
|
|
92
|
+
</Select>
|
|
93
|
+
</Grid>
|
|
94
|
+
</Grid>
|
|
95
|
+
{ isCustom && (
|
|
96
|
+
<Grid container gap={ 2 } alignItems="center" flexWrap="nowrap">
|
|
97
|
+
<Grid item xs={ 6 }>
|
|
98
|
+
<TextField
|
|
99
|
+
size="tiny"
|
|
100
|
+
type="number"
|
|
101
|
+
fullWidth
|
|
102
|
+
value={ customWidth }
|
|
103
|
+
onChange={ handleCustomWidthChange }
|
|
104
|
+
placeholder={ __( 'Width', 'elementor' ) }
|
|
105
|
+
/>
|
|
106
|
+
</Grid>
|
|
107
|
+
<Grid item xs={ 6 }>
|
|
108
|
+
<TextField
|
|
109
|
+
size="tiny"
|
|
110
|
+
type="number"
|
|
111
|
+
fullWidth
|
|
112
|
+
value={ customHeight }
|
|
113
|
+
onChange={ handleCustomHeightChange }
|
|
114
|
+
placeholder={ __( 'Height', 'elementor' ) }
|
|
115
|
+
/>
|
|
116
|
+
</Grid>
|
|
117
|
+
</Grid>
|
|
118
|
+
) }
|
|
119
|
+
</Stack>
|
|
120
|
+
);
|
|
121
|
+
} );
|
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
2
|
import { backgroundPropTypeUtil } from '@elementor/editor-props';
|
|
3
|
+
import { isExperimentActive } from '@elementor/editor-v1-adapters';
|
|
3
4
|
import { Grid } from '@elementor/ui';
|
|
4
5
|
import { __ } from '@wordpress/i18n';
|
|
5
6
|
|
|
6
7
|
import { PropKeyProvider, PropProvider, useBoundProp } from '../../bound-prop-context';
|
|
7
8
|
import { ControlFormLabel } from '../../components/control-form-label';
|
|
9
|
+
import { ControlLabel } from '../../components/control-label';
|
|
8
10
|
import { SectionContent } from '../../components/section-content';
|
|
9
11
|
import { createControl } from '../../create-control';
|
|
10
12
|
import { ColorControl } from '../color-control';
|
|
@@ -12,6 +14,9 @@ import { BackgroundOverlayRepeaterControl } from './background-overlay/backgroun
|
|
|
12
14
|
|
|
13
15
|
export const BackgroundControl = createControl( () => {
|
|
14
16
|
const propContext = useBoundProp( backgroundPropTypeUtil );
|
|
17
|
+
const isUsingNestedProps = isExperimentActive( 'e_v_3_30' );
|
|
18
|
+
|
|
19
|
+
const colorLabel = __( 'Color', 'elementor' );
|
|
15
20
|
|
|
16
21
|
return (
|
|
17
22
|
<PropProvider { ...propContext }>
|
|
@@ -22,7 +27,11 @@ export const BackgroundControl = createControl( () => {
|
|
|
22
27
|
<PropKeyProvider bind="color">
|
|
23
28
|
<Grid container gap={ 2 } alignItems="center" flexWrap="nowrap">
|
|
24
29
|
<Grid item xs={ 6 }>
|
|
25
|
-
|
|
30
|
+
{ isUsingNestedProps ? (
|
|
31
|
+
<ControlLabel>{ colorLabel }</ControlLabel>
|
|
32
|
+
) : (
|
|
33
|
+
<ControlFormLabel>{ colorLabel }</ControlFormLabel>
|
|
34
|
+
) }
|
|
26
35
|
</Grid>
|
|
27
36
|
<Grid item xs={ 6 }>
|
|
28
37
|
<ColorControl />
|
package/src/controls/background-control/background-overlay/background-overlay-repeater-control.tsx
CHANGED
|
@@ -91,15 +91,15 @@ export const BackgroundOverlayRepeaterControl = createControl( () => {
|
|
|
91
91
|
);
|
|
92
92
|
} );
|
|
93
93
|
|
|
94
|
-
export const ItemContent = ( { bind }: { bind: PropKey } ) => {
|
|
94
|
+
export const ItemContent = ( { anchorEl = null, bind }: { anchorEl?: HTMLElement | null; bind: PropKey } ) => {
|
|
95
95
|
return (
|
|
96
96
|
<PropKeyProvider bind={ bind }>
|
|
97
|
-
<Content />
|
|
97
|
+
<Content anchorEl={ anchorEl } />
|
|
98
98
|
</PropKeyProvider>
|
|
99
99
|
);
|
|
100
100
|
};
|
|
101
101
|
|
|
102
|
-
const Content = () => {
|
|
102
|
+
const Content = ( { anchorEl }: { anchorEl: HTMLElement | null } ) => {
|
|
103
103
|
const { getTabsProps, getTabProps, getTabPanelProps } = useBackgroundTabsHistory( {
|
|
104
104
|
image: getInitialBackgroundOverlay().value,
|
|
105
105
|
color: initialBackgroundColorOverlay.value,
|
|
@@ -130,7 +130,7 @@ const Content = () => {
|
|
|
130
130
|
</TabPanel>
|
|
131
131
|
<TabPanel sx={ { p: 1.5 } } { ...getTabPanelProps( 'color' ) }>
|
|
132
132
|
<PopoverContent>
|
|
133
|
-
<ColorOverlayContent />
|
|
133
|
+
<ColorOverlayContent anchorEl={ anchorEl } />
|
|
134
134
|
</PopoverContent>
|
|
135
135
|
</TabPanel>
|
|
136
136
|
</Box>
|
|
@@ -217,12 +217,12 @@ const ItemLabelGradient = ( { value }: { value: BackgroundOverlayItemPropValue }
|
|
|
217
217
|
return <span>{ __( 'Radial Gradient', 'elementor' ) }</span>;
|
|
218
218
|
};
|
|
219
219
|
|
|
220
|
-
const ColorOverlayContent = () => {
|
|
220
|
+
const ColorOverlayContent = ( { anchorEl }: { anchorEl: HTMLElement | null } ) => {
|
|
221
221
|
const propContext = useBoundProp( backgroundColorOverlayPropTypeUtil );
|
|
222
222
|
return (
|
|
223
223
|
<PropProvider { ...propContext }>
|
|
224
224
|
<PropKeyProvider bind={ 'color' }>
|
|
225
|
-
<ColorControl />
|
|
225
|
+
<ColorControl anchorEl={ anchorEl } />
|
|
226
226
|
</PropKeyProvider>
|
|
227
227
|
</PropProvider>
|
|
228
228
|
);
|
|
@@ -53,21 +53,7 @@ const Content = ( { anchorEl }: { anchorEl: HTMLElement | null } ) => {
|
|
|
53
53
|
<PopoverContent p={ 1.5 }>
|
|
54
54
|
<PopoverGridContainer>
|
|
55
55
|
<Control bind="color" label={ __( 'Color', 'elementor' ) }>
|
|
56
|
-
<ColorControl
|
|
57
|
-
slotProps={ {
|
|
58
|
-
colorPicker: {
|
|
59
|
-
anchorEl,
|
|
60
|
-
anchorOrigin: {
|
|
61
|
-
vertical: 'top',
|
|
62
|
-
horizontal: 'right',
|
|
63
|
-
},
|
|
64
|
-
transformOrigin: {
|
|
65
|
-
vertical: 'top',
|
|
66
|
-
horizontal: -10,
|
|
67
|
-
},
|
|
68
|
-
},
|
|
69
|
-
} }
|
|
70
|
-
/>
|
|
56
|
+
<ColorControl anchorEl={ anchorEl } />
|
|
71
57
|
</Control>
|
|
72
58
|
<Control bind="position" label={ __( 'Position', 'elementor' ) } sx={ { overflow: 'hidden' } }>
|
|
73
59
|
<SelectControl
|
|
@@ -8,18 +8,41 @@ import { createControl } from '../create-control';
|
|
|
8
8
|
|
|
9
9
|
type Props = Partial< Omit< UnstableColorFieldProps, 'value' | 'onChange' > > & {
|
|
10
10
|
propTypeUtil?: PropTypeUtil< string, string >;
|
|
11
|
+
anchorEl?: HTMLElement | null;
|
|
11
12
|
};
|
|
12
13
|
|
|
13
|
-
export const ColorControl = createControl(
|
|
14
|
-
|
|
14
|
+
export const ColorControl = createControl(
|
|
15
|
+
( { propTypeUtil = colorPropTypeUtil, anchorEl, slotProps = {}, ...props }: Props ) => {
|
|
16
|
+
const { value, setValue } = useBoundProp( propTypeUtil );
|
|
15
17
|
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
18
|
+
const handleChange = ( selectedColor: string ) => {
|
|
19
|
+
setValue( selectedColor || null );
|
|
20
|
+
};
|
|
19
21
|
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
}
|
|
22
|
+
return (
|
|
23
|
+
<ControlActions>
|
|
24
|
+
<UnstableColorField
|
|
25
|
+
size="tiny"
|
|
26
|
+
fullWidth
|
|
27
|
+
value={ value ?? '' }
|
|
28
|
+
onChange={ handleChange }
|
|
29
|
+
{ ...props }
|
|
30
|
+
slotProps={ {
|
|
31
|
+
...slotProps,
|
|
32
|
+
colorPicker: {
|
|
33
|
+
anchorEl,
|
|
34
|
+
anchorOrigin: {
|
|
35
|
+
vertical: 'top',
|
|
36
|
+
horizontal: 'right',
|
|
37
|
+
},
|
|
38
|
+
transformOrigin: {
|
|
39
|
+
vertical: 'top',
|
|
40
|
+
horizontal: -10,
|
|
41
|
+
},
|
|
42
|
+
},
|
|
43
|
+
} }
|
|
44
|
+
/>
|
|
45
|
+
</ControlActions>
|
|
46
|
+
);
|
|
47
|
+
}
|
|
48
|
+
);
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
+
import { useRef } from 'react';
|
|
2
3
|
import { sizePropTypeUtil, stringPropTypeUtil } from '@elementor/editor-props';
|
|
3
4
|
import { InputAdornment } from '@elementor/ui';
|
|
4
5
|
|
|
@@ -116,6 +117,31 @@ const SizeInput = ( {
|
|
|
116
117
|
size,
|
|
117
118
|
unit,
|
|
118
119
|
}: SizeInputProps ) => {
|
|
120
|
+
const unitInputBufferRef = useRef( '' );
|
|
121
|
+
|
|
122
|
+
const handleKeyUp = ( event: React.KeyboardEvent< HTMLInputElement > ) => {
|
|
123
|
+
const { key } = event;
|
|
124
|
+
|
|
125
|
+
if ( ! /^[a-zA-Z%]$/.test( key ) ) {
|
|
126
|
+
return;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
event.preventDefault();
|
|
130
|
+
|
|
131
|
+
const newChar = key.toLowerCase();
|
|
132
|
+
const updatedBuffer = ( unitInputBufferRef.current + newChar ).slice( -3 );
|
|
133
|
+
unitInputBufferRef.current = updatedBuffer;
|
|
134
|
+
|
|
135
|
+
const matchedUnit =
|
|
136
|
+
units.find( ( u ) => u.includes( updatedBuffer ) ) ||
|
|
137
|
+
units.find( ( u ) => u.startsWith( newChar ) ) ||
|
|
138
|
+
units.find( ( u ) => u.includes( newChar ) );
|
|
139
|
+
|
|
140
|
+
if ( matchedUnit ) {
|
|
141
|
+
handleUnitChange( matchedUnit );
|
|
142
|
+
}
|
|
143
|
+
};
|
|
144
|
+
|
|
119
145
|
return (
|
|
120
146
|
<ControlActions>
|
|
121
147
|
<TextFieldInnerSelection
|
|
@@ -133,12 +159,16 @@ const SizeInput = ( {
|
|
|
133
159
|
type="number"
|
|
134
160
|
value={ Number.isNaN( size ) ? '' : size }
|
|
135
161
|
onChange={ handleSizeChange }
|
|
136
|
-
onBlur={
|
|
162
|
+
onBlur={ ( event ) => {
|
|
163
|
+
unitInputBufferRef.current = '';
|
|
164
|
+
onBlur?.( event );
|
|
165
|
+
} }
|
|
137
166
|
onKeyDown={ ( event ) => {
|
|
138
167
|
if ( RESTRICTED_INPUT_KEYS.includes( event.key ) ) {
|
|
139
168
|
event.preventDefault();
|
|
140
169
|
}
|
|
141
170
|
} }
|
|
171
|
+
onKeyUp={ handleKeyUp }
|
|
142
172
|
/>
|
|
143
173
|
</ControlActions>
|
|
144
174
|
);
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import * as React from 'react';
|
|
2
|
+
import { booleanPropTypeUtil } from '@elementor/editor-props';
|
|
3
|
+
import { Switch } from '@elementor/ui';
|
|
4
|
+
|
|
5
|
+
import { useBoundProp } from '../bound-prop-context/use-bound-prop';
|
|
6
|
+
import { createControl } from '../create-control';
|
|
7
|
+
|
|
8
|
+
export const SwitchControl = createControl( () => {
|
|
9
|
+
const { value, setValue } = useBoundProp( booleanPropTypeUtil );
|
|
10
|
+
|
|
11
|
+
const handleChange = ( event: React.ChangeEvent< HTMLInputElement > ) => {
|
|
12
|
+
setValue( event.target.checked );
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
return (
|
|
16
|
+
<div style={ { display: 'flex', justifyContent: 'flex-end' } }>
|
|
17
|
+
<Switch checked={ !! value } onChange={ handleChange } size="small" />
|
|
18
|
+
</div>
|
|
19
|
+
);
|
|
20
|
+
} );
|
package/src/index.ts
CHANGED
|
@@ -15,8 +15,10 @@ export { FontFamilyControl } from './controls/font-family-control/font-family-co
|
|
|
15
15
|
export { UrlControl } from './controls/url-control';
|
|
16
16
|
export { LinkControl } from './controls/link-control';
|
|
17
17
|
export { GapControl } from './controls/gap-control';
|
|
18
|
+
export { AspectRatioControl } from './controls/aspect-ratio-control';
|
|
18
19
|
export { SvgMediaControl } from './controls/svg-media-control';
|
|
19
20
|
export { BackgroundControl } from './controls/background-control/background-control';
|
|
21
|
+
export { SwitchControl } from './controls/switch-control';
|
|
20
22
|
|
|
21
23
|
// components
|
|
22
24
|
export { ControlFormLabel } from './components/control-form-label';
|