@elementor/editor-components 4.0.0-665 → 4.0.0-667
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/dist/index.js +191 -3870
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +184 -3904
- package/dist/index.mjs.map +1 -1
- package/package.json +23 -23
- package/src/init.ts +0 -13
- package/src/extended/components/component-introduction.tsx +0 -77
- package/src/extended/components/component-panel-header/component-badge.tsx +0 -73
- package/src/extended/components/component-panel-header/component-panel-header.tsx +0 -98
- package/src/extended/components/component-properties-panel/component-properties-panel-content.tsx +0 -176
- package/src/extended/components/component-properties-panel/component-properties-panel.tsx +0 -43
- package/src/extended/components/component-properties-panel/properties-empty-state.tsx +0 -51
- package/src/extended/components/component-properties-panel/properties-group.tsx +0 -196
- package/src/extended/components/component-properties-panel/property-item.tsx +0 -124
- package/src/extended/components/component-properties-panel/sortable.tsx +0 -92
- package/src/extended/components/component-properties-panel/use-current-editable-item.ts +0 -73
- package/src/extended/components/component-properties-panel/utils/generate-unique-label.ts +0 -21
- package/src/extended/components/component-properties-panel/utils/validate-group-label.ts +0 -24
- package/src/extended/components/components-tab/component-item.tsx +0 -180
- package/src/extended/components/components-tab/components.tsx +0 -58
- package/src/extended/components/components-tab/delete-confirmation-dialog.tsx +0 -26
- package/src/extended/components/create-component-form/create-component-form.tsx +0 -281
- package/src/extended/components/create-component-form/hooks/use-form.ts +0 -72
- package/src/extended/components/create-component-form/utils/get-component-event-data.ts +0 -54
- package/src/extended/components/edit-component/component-modal.tsx +0 -133
- package/src/extended/components/edit-component/edit-component.tsx +0 -166
- package/src/extended/components/edit-component/use-canvas-document.ts +0 -9
- package/src/extended/components/edit-component/use-element-rect.ts +0 -81
- package/src/extended/components/instance-editing-panel/instance-editing-panel.tsx +0 -60
- package/src/extended/components/overridable-props/indicator.tsx +0 -83
- package/src/extended/components/overridable-props/overridable-prop-control.tsx +0 -127
- package/src/extended/components/overridable-props/overridable-prop-form.tsx +0 -135
- package/src/extended/components/overridable-props/overridable-prop-indicator.tsx +0 -138
- package/src/extended/components/overridable-props/utils/validate-prop-label.ts +0 -38
- package/src/extended/consts.ts +0 -3
- package/src/extended/hooks/use-navigate-back.ts +0 -24
- package/src/extended/init.ts +0 -108
- package/src/extended/mcp/index.ts +0 -14
- package/src/extended/mcp/save-as-component-tool.ts +0 -436
- package/src/extended/shortcuts/create-component-shortcut.ts +0 -121
- package/src/extended/store/actions/add-overridable-group.ts +0 -53
- package/src/extended/store/actions/archive-component.ts +0 -18
- package/src/extended/store/actions/create-unpublished-component.ts +0 -99
- package/src/extended/store/actions/delete-overridable-group.ts +0 -32
- package/src/extended/store/actions/delete-overridable-prop.ts +0 -64
- package/src/extended/store/actions/rename-component.ts +0 -48
- package/src/extended/store/actions/rename-overridable-group.ts +0 -33
- package/src/extended/store/actions/reorder-group-props.ts +0 -37
- package/src/extended/store/actions/reorder-overridable-groups.ts +0 -24
- package/src/extended/store/actions/reset-sanitized-components.ts +0 -5
- package/src/extended/store/actions/set-overridable-prop.ts +0 -109
- package/src/extended/store/actions/update-component-sanitized-attribute.ts +0 -7
- package/src/extended/store/actions/update-current-component.ts +0 -12
- package/src/extended/store/actions/update-overridable-prop-params.ts +0 -52
- package/src/extended/store/utils/groups-transformers.ts +0 -187
- package/src/extended/sync/before-save.ts +0 -52
- package/src/extended/sync/cleanup-overridable-props-on-delete.ts +0 -78
- package/src/extended/sync/create-components-before-save.ts +0 -111
- package/src/extended/sync/handle-component-edit-mode-container.ts +0 -114
- package/src/extended/sync/prevent-non-atomic-nesting.ts +0 -198
- package/src/extended/sync/revert-overridables-on-copy-or-duplicate.ts +0 -66
- package/src/extended/sync/sanitize-overridable-props.ts +0 -32
- package/src/extended/sync/set-component-overridable-props-settings-before-save.ts +0 -22
- package/src/extended/sync/update-archived-component-before-save.ts +0 -31
- package/src/extended/sync/update-component-title-before-save.ts +0 -18
- package/src/extended/utils/component-form-schema.ts +0 -32
- package/src/extended/utils/component-name-validation.ts +0 -25
- package/src/extended/utils/create-component-model.ts +0 -28
- package/src/extended/utils/get-container-for-new-element.ts +0 -49
- package/src/extended/utils/is-editing-component.ts +0 -5
- package/src/extended/utils/replace-element-with-component.ts +0 -11
- package/src/extended/utils/revert-overridable-settings.ts +0 -207
|
@@ -1,187 +0,0 @@
|
|
|
1
|
-
import { generateUniqueId } from '@elementor/utils';
|
|
2
|
-
import { __ } from '@wordpress/i18n';
|
|
3
|
-
|
|
4
|
-
import { type OverridableProp, type OverridableProps, type OverridablePropsGroup } from '../../../types';
|
|
5
|
-
|
|
6
|
-
type Groups = OverridableProps[ 'groups' ];
|
|
7
|
-
|
|
8
|
-
export function removePropFromAllGroups( groups: Groups, propKey: string | string[] ): Groups {
|
|
9
|
-
const propKeys = Array.isArray( propKey ) ? propKey : [ propKey ];
|
|
10
|
-
|
|
11
|
-
return {
|
|
12
|
-
...groups,
|
|
13
|
-
items: Object.fromEntries(
|
|
14
|
-
Object.entries( groups.items ).map( ( [ groupId, group ] ) => [
|
|
15
|
-
groupId,
|
|
16
|
-
{
|
|
17
|
-
...group,
|
|
18
|
-
props: group.props.filter( ( p ) => ! propKeys.includes( p ) ),
|
|
19
|
-
},
|
|
20
|
-
] )
|
|
21
|
-
),
|
|
22
|
-
};
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
export function addPropToGroup( groups: Groups, groupId: string, propKey: string ): Groups {
|
|
26
|
-
const group = groups.items[ groupId ];
|
|
27
|
-
|
|
28
|
-
if ( ! group ) {
|
|
29
|
-
return groups;
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
if ( group.props.includes( propKey ) ) {
|
|
33
|
-
return groups;
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
return {
|
|
37
|
-
...groups,
|
|
38
|
-
items: {
|
|
39
|
-
...groups.items,
|
|
40
|
-
[ groupId ]: {
|
|
41
|
-
...group,
|
|
42
|
-
props: [ ...group.props, propKey ],
|
|
43
|
-
},
|
|
44
|
-
},
|
|
45
|
-
};
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
export function movePropBetweenGroups(
|
|
49
|
-
groups: Groups,
|
|
50
|
-
propKey: string,
|
|
51
|
-
fromGroupId: string,
|
|
52
|
-
toGroupId: string
|
|
53
|
-
): Groups {
|
|
54
|
-
if ( fromGroupId === toGroupId ) {
|
|
55
|
-
return groups;
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
const withoutProp = removePropFromGroup( groups, fromGroupId, propKey );
|
|
59
|
-
return addPropToGroup( withoutProp, toGroupId, propKey );
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
export function removePropFromGroup( groups: Groups, groupId: string, propKey: string ): Groups {
|
|
63
|
-
const group = groups.items[ groupId ];
|
|
64
|
-
|
|
65
|
-
if ( ! group ) {
|
|
66
|
-
return groups;
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
return {
|
|
70
|
-
...groups,
|
|
71
|
-
items: {
|
|
72
|
-
...groups.items,
|
|
73
|
-
[ groupId ]: {
|
|
74
|
-
...group,
|
|
75
|
-
props: group.props.filter( ( p ) => p !== propKey ),
|
|
76
|
-
},
|
|
77
|
-
},
|
|
78
|
-
};
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
type ResolvedGroup = {
|
|
82
|
-
groups: Groups;
|
|
83
|
-
groupId: string;
|
|
84
|
-
};
|
|
85
|
-
|
|
86
|
-
export function resolveOrCreateGroup( groups: Groups, requestedGroupId?: string ): ResolvedGroup {
|
|
87
|
-
if ( requestedGroupId && groups.items[ requestedGroupId ] ) {
|
|
88
|
-
return { groups, groupId: requestedGroupId };
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
if ( ! requestedGroupId && groups.order.length > 0 ) {
|
|
92
|
-
return { groups, groupId: groups.order[ 0 ] };
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
return createGroup( groups, requestedGroupId );
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
function createGroup( groups: Groups, groupId?: string, label?: string ): ResolvedGroup {
|
|
99
|
-
const newGroupId = groupId || generateUniqueId( 'group' );
|
|
100
|
-
const newLabel = label || __( 'Default', 'elementor' );
|
|
101
|
-
|
|
102
|
-
return {
|
|
103
|
-
groups: {
|
|
104
|
-
...groups,
|
|
105
|
-
items: {
|
|
106
|
-
...groups.items,
|
|
107
|
-
[ newGroupId ]: {
|
|
108
|
-
id: newGroupId,
|
|
109
|
-
label: newLabel,
|
|
110
|
-
props: [],
|
|
111
|
-
},
|
|
112
|
-
},
|
|
113
|
-
order: [ ...groups.order, newGroupId ],
|
|
114
|
-
},
|
|
115
|
-
groupId: newGroupId,
|
|
116
|
-
};
|
|
117
|
-
}
|
|
118
|
-
|
|
119
|
-
export function removePropsFromState(
|
|
120
|
-
overridableProps: OverridableProps,
|
|
121
|
-
propsToRemove: OverridableProp[]
|
|
122
|
-
): OverridableProps {
|
|
123
|
-
const overrideKeysToRemove = propsToRemove.map( ( prop ) => prop.overrideKey );
|
|
124
|
-
|
|
125
|
-
const remainingProps = Object.fromEntries(
|
|
126
|
-
Object.entries( overridableProps.props ).filter( ( [ , prop ] ) => ! propsToRemove.includes( prop ) )
|
|
127
|
-
);
|
|
128
|
-
|
|
129
|
-
const updatedGroupItems = Object.fromEntries(
|
|
130
|
-
Object.entries( overridableProps.groups.items ).map(
|
|
131
|
-
( [ groupId, group ]: [ string, OverridablePropsGroup ] ) => [
|
|
132
|
-
groupId,
|
|
133
|
-
{
|
|
134
|
-
...group,
|
|
135
|
-
props: group.props.filter( ( prop ) => ! overrideKeysToRemove.includes( prop ) ),
|
|
136
|
-
},
|
|
137
|
-
]
|
|
138
|
-
)
|
|
139
|
-
);
|
|
140
|
-
|
|
141
|
-
return {
|
|
142
|
-
props: remainingProps,
|
|
143
|
-
groups: {
|
|
144
|
-
items: updatedGroupItems,
|
|
145
|
-
order: overridableProps.groups.order.filter( ( groupId ) => ! overrideKeysToRemove.includes( groupId ) ),
|
|
146
|
-
},
|
|
147
|
-
};
|
|
148
|
-
}
|
|
149
|
-
|
|
150
|
-
export function ensureGroupInOrder( groups: Groups, groupId: string ): Groups {
|
|
151
|
-
if ( groups.order.includes( groupId ) ) {
|
|
152
|
-
return groups;
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
return {
|
|
156
|
-
...groups,
|
|
157
|
-
order: [ ...groups.order, groupId ],
|
|
158
|
-
};
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
export function deleteGroup( groups: Groups, groupId: string ): Groups {
|
|
162
|
-
const { [ groupId ]: removed, ...remainingItems } = groups.items;
|
|
163
|
-
|
|
164
|
-
return {
|
|
165
|
-
items: remainingItems,
|
|
166
|
-
order: groups.order.filter( ( id ) => id !== groupId ),
|
|
167
|
-
};
|
|
168
|
-
}
|
|
169
|
-
|
|
170
|
-
export function renameGroup( groups: Groups, groupId: string, newLabel: string ): Groups {
|
|
171
|
-
const group = groups.items[ groupId ];
|
|
172
|
-
|
|
173
|
-
if ( ! group ) {
|
|
174
|
-
return groups;
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
return {
|
|
178
|
-
...groups,
|
|
179
|
-
items: {
|
|
180
|
-
...groups.items,
|
|
181
|
-
[ groupId ]: {
|
|
182
|
-
...group,
|
|
183
|
-
label: newLabel,
|
|
184
|
-
},
|
|
185
|
-
},
|
|
186
|
-
};
|
|
187
|
-
}
|
|
@@ -1,52 +0,0 @@
|
|
|
1
|
-
import { type V1Document } from '@elementor/editor-documents';
|
|
2
|
-
import { type V1Element, type V1ElementData } from '@elementor/editor-elements';
|
|
3
|
-
|
|
4
|
-
import { publishDraftComponentsInPageBeforeSave } from '../../sync/publish-draft-components-in-page-before-save';
|
|
5
|
-
import { type DocumentSaveStatus } from '../../types';
|
|
6
|
-
import { setComponentOverridablePropsSettingsBeforeSave } from '../sync/set-component-overridable-props-settings-before-save';
|
|
7
|
-
import { updateArchivedComponentBeforeSave } from '../sync/update-archived-component-before-save';
|
|
8
|
-
import { updateComponentTitleBeforeSave } from '../sync/update-component-title-before-save';
|
|
9
|
-
import { createComponentsBeforeSave } from './create-components-before-save';
|
|
10
|
-
|
|
11
|
-
type Options = {
|
|
12
|
-
container: V1Element & {
|
|
13
|
-
document: V1Document;
|
|
14
|
-
model: {
|
|
15
|
-
get: ( key: 'elements' ) => {
|
|
16
|
-
toJSON: () => V1ElementData[];
|
|
17
|
-
};
|
|
18
|
-
};
|
|
19
|
-
};
|
|
20
|
-
status: DocumentSaveStatus;
|
|
21
|
-
};
|
|
22
|
-
|
|
23
|
-
export const beforeSave = ( { container, status }: Options ) => {
|
|
24
|
-
const elements = container?.model.get( 'elements' ).toJSON?.() ?? [];
|
|
25
|
-
|
|
26
|
-
return Promise.all( [
|
|
27
|
-
syncComponents( { elements, status } ),
|
|
28
|
-
setComponentOverridablePropsSettingsBeforeSave( { container } ),
|
|
29
|
-
] );
|
|
30
|
-
};
|
|
31
|
-
|
|
32
|
-
// These operations run sequentially to prevent race conditions when multiple
|
|
33
|
-
// edits occur on the same component simultaneously.
|
|
34
|
-
// TODO: Consolidate these into a single PUT /components endpoint.
|
|
35
|
-
const syncComponents = async ( { elements, status }: { elements: V1ElementData[]; status: DocumentSaveStatus } ) => {
|
|
36
|
-
// This order is important - first update existing components, then create new components,
|
|
37
|
-
// Since new component validation depends on the existing components (preventing duplicate names).
|
|
38
|
-
await updateExistingComponentsBeforeSave( { elements, status } );
|
|
39
|
-
await createComponentsBeforeSave( { elements, status } );
|
|
40
|
-
};
|
|
41
|
-
|
|
42
|
-
const updateExistingComponentsBeforeSave = async ( {
|
|
43
|
-
elements,
|
|
44
|
-
status,
|
|
45
|
-
}: {
|
|
46
|
-
elements: V1ElementData[];
|
|
47
|
-
status: DocumentSaveStatus;
|
|
48
|
-
} ) => {
|
|
49
|
-
await updateComponentTitleBeforeSave( status );
|
|
50
|
-
await updateArchivedComponentBeforeSave( status );
|
|
51
|
-
await publishDraftComponentsInPageBeforeSave( { elements, status } );
|
|
52
|
-
};
|
|
@@ -1,78 +0,0 @@
|
|
|
1
|
-
import { getAllDescendants, type V1Element } from '@elementor/editor-elements';
|
|
2
|
-
import { type HookOptions, registerDataHook } from '@elementor/editor-v1-adapters';
|
|
3
|
-
|
|
4
|
-
import { componentsSelectors } from '../../store/selectors';
|
|
5
|
-
import { deleteOverridableProp } from '../store/actions/delete-overridable-prop';
|
|
6
|
-
|
|
7
|
-
type DeleteCommandArgs = {
|
|
8
|
-
container?: V1Element;
|
|
9
|
-
containers?: V1Element[];
|
|
10
|
-
};
|
|
11
|
-
|
|
12
|
-
export function initCleanupOverridablePropsOnDelete() {
|
|
13
|
-
// This hook is not a real dependency - it doesn't block the execution of the command in any case, only perform side effect.
|
|
14
|
-
// We use `dependency` and not `after` hook because the `after` hook doesn't include the children of a deleted container
|
|
15
|
-
// in the callback parameters (as they already were deleted).
|
|
16
|
-
registerDataHook( 'dependency', 'document/elements/delete', ( args: DeleteCommandArgs, options?: HookOptions ) => {
|
|
17
|
-
if ( isPartOfMoveCommand( options ) ) {
|
|
18
|
-
return true;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
const currentComponentId = componentsSelectors.getCurrentComponentId();
|
|
22
|
-
|
|
23
|
-
if ( ! currentComponentId ) {
|
|
24
|
-
return true;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
const overridableProps = componentsSelectors.getOverridableProps( currentComponentId );
|
|
28
|
-
|
|
29
|
-
if ( ! overridableProps || Object.keys( overridableProps.props ).length === 0 ) {
|
|
30
|
-
return true;
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
const containers = args.containers ?? ( args.container ? [ args.container ] : [] );
|
|
34
|
-
|
|
35
|
-
if ( containers.length === 0 ) {
|
|
36
|
-
return true;
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
const deletedElementIds = collectDeletedElementIds( containers );
|
|
40
|
-
|
|
41
|
-
if ( deletedElementIds.length === 0 ) {
|
|
42
|
-
return true;
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
const propKeysToDelete = Object.entries( overridableProps.props )
|
|
46
|
-
.filter( ( [ , prop ] ) => deletedElementIds.includes( prop.elementId ) )
|
|
47
|
-
.map( ( [ propKey ] ) => propKey );
|
|
48
|
-
|
|
49
|
-
if ( propKeysToDelete.length === 0 ) {
|
|
50
|
-
return true;
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
deleteOverridableProp( { componentId: currentComponentId, propKey: propKeysToDelete, source: 'system' } );
|
|
54
|
-
|
|
55
|
-
return true;
|
|
56
|
-
} );
|
|
57
|
-
}
|
|
58
|
-
|
|
59
|
-
function collectDeletedElementIds( containers: V1Element[] ): string[] {
|
|
60
|
-
const elementIds = containers
|
|
61
|
-
.filter( Boolean )
|
|
62
|
-
.flatMap( ( container ) => [ container, ...getAllDescendants( container ) ] )
|
|
63
|
-
.map( ( element ) => element.model?.get?.( 'id' ) ?? element.id )
|
|
64
|
-
.filter( ( id ): id is string => Boolean( id ) );
|
|
65
|
-
|
|
66
|
-
return elementIds;
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
function isPartOfMoveCommand( options?: HookOptions ): boolean {
|
|
70
|
-
// Skip cleanup if this delete is part of a move command
|
|
71
|
-
// Move = delete + create, and we don't want to delete the overridable prop in this case.
|
|
72
|
-
// See assets/dev/js/editor/document/elements/commands/move.js
|
|
73
|
-
const isMoveCommandInTrace =
|
|
74
|
-
options?.commandsCurrentTrace?.includes( 'document/elements/move' ) ||
|
|
75
|
-
options?.commandsCurrentTrace?.includes( 'document/repeater/move' );
|
|
76
|
-
|
|
77
|
-
return Boolean( isMoveCommandInTrace );
|
|
78
|
-
}
|
|
@@ -1,111 +0,0 @@
|
|
|
1
|
-
import { updateElementSettings, type V1ElementData } from '@elementor/editor-elements';
|
|
2
|
-
|
|
3
|
-
import { apiClient } from '../../api';
|
|
4
|
-
import { type ComponentInstanceProp } from '../../prop-types/component-instance-prop-type';
|
|
5
|
-
import { componentsActions } from '../../store/dispatchers';
|
|
6
|
-
import { componentsSelectors } from '../../store/selectors';
|
|
7
|
-
import { type DocumentSaveStatus, type UnpublishedComponent } from '../../types';
|
|
8
|
-
|
|
9
|
-
export async function createComponentsBeforeSave( {
|
|
10
|
-
elements,
|
|
11
|
-
status,
|
|
12
|
-
}: {
|
|
13
|
-
elements: V1ElementData[];
|
|
14
|
-
status: DocumentSaveStatus;
|
|
15
|
-
} ) {
|
|
16
|
-
const unpublishedComponents = componentsSelectors.getUnpublishedComponents();
|
|
17
|
-
|
|
18
|
-
if ( ! unpublishedComponents.length ) {
|
|
19
|
-
return;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
try {
|
|
23
|
-
const uidToComponentId = await createComponents( unpublishedComponents, status );
|
|
24
|
-
|
|
25
|
-
updateComponentInstances( elements, uidToComponentId );
|
|
26
|
-
|
|
27
|
-
componentsActions.add(
|
|
28
|
-
unpublishedComponents.map( ( component ) => ( {
|
|
29
|
-
id: uidToComponentId.get( component.uid ) as number,
|
|
30
|
-
name: component.name,
|
|
31
|
-
uid: component.uid,
|
|
32
|
-
overridableProps: component.overridableProps ? component.overridableProps : undefined,
|
|
33
|
-
} ) )
|
|
34
|
-
);
|
|
35
|
-
componentsActions.resetUnpublished();
|
|
36
|
-
} catch ( error ) {
|
|
37
|
-
const failedUids = unpublishedComponents.map( ( component ) => component.uid );
|
|
38
|
-
componentsActions.removeUnpublished( failedUids );
|
|
39
|
-
|
|
40
|
-
throw new Error( `Failed to publish components: ${ error }` );
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
async function createComponents(
|
|
45
|
-
components: UnpublishedComponent[],
|
|
46
|
-
status: DocumentSaveStatus
|
|
47
|
-
): Promise< Map< string, number > > {
|
|
48
|
-
const response = await apiClient.create( {
|
|
49
|
-
status,
|
|
50
|
-
items: components.map( ( component ) => ( {
|
|
51
|
-
uid: component.uid,
|
|
52
|
-
title: component.name,
|
|
53
|
-
elements: component.elements,
|
|
54
|
-
settings: component.overridableProps ? { overridable_props: component.overridableProps } : undefined,
|
|
55
|
-
} ) ),
|
|
56
|
-
} );
|
|
57
|
-
|
|
58
|
-
const map = new Map< string, number >();
|
|
59
|
-
|
|
60
|
-
Object.entries( response ).forEach( ( [ key, value ] ) => {
|
|
61
|
-
map.set( key, value );
|
|
62
|
-
} );
|
|
63
|
-
|
|
64
|
-
return map;
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
function updateComponentInstances( elements: V1ElementData[], uidToComponentId: Map< string, number > ): void {
|
|
68
|
-
elements.forEach( ( element ) => {
|
|
69
|
-
const { shouldUpdate, newComponentId } = shouldUpdateElement( element, uidToComponentId );
|
|
70
|
-
if ( shouldUpdate ) {
|
|
71
|
-
updateElementComponentId( element.id, newComponentId );
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
if ( element.elements ) {
|
|
75
|
-
updateComponentInstances( element.elements, uidToComponentId );
|
|
76
|
-
}
|
|
77
|
-
} );
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
function shouldUpdateElement(
|
|
81
|
-
element: V1ElementData,
|
|
82
|
-
uidToComponentId: Map< string, number >
|
|
83
|
-
): { shouldUpdate: true; newComponentId: number } | { shouldUpdate: false; newComponentId: null } {
|
|
84
|
-
if ( element.widgetType === 'e-component' ) {
|
|
85
|
-
const currentComponentId = ( element.settings?.component_instance as ComponentInstanceProp )?.value
|
|
86
|
-
?.component_id.value;
|
|
87
|
-
|
|
88
|
-
if ( currentComponentId && uidToComponentId.has( currentComponentId.toString() ) ) {
|
|
89
|
-
return {
|
|
90
|
-
shouldUpdate: true,
|
|
91
|
-
newComponentId: uidToComponentId.get( currentComponentId.toString() ) as number,
|
|
92
|
-
};
|
|
93
|
-
}
|
|
94
|
-
}
|
|
95
|
-
return { shouldUpdate: false, newComponentId: null };
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
function updateElementComponentId( elementId: string, componentId: number ): void {
|
|
99
|
-
updateElementSettings( {
|
|
100
|
-
id: elementId,
|
|
101
|
-
props: {
|
|
102
|
-
component_instance: {
|
|
103
|
-
$$type: 'component-instance',
|
|
104
|
-
value: {
|
|
105
|
-
component_id: { $$type: 'number', value: componentId },
|
|
106
|
-
},
|
|
107
|
-
},
|
|
108
|
-
},
|
|
109
|
-
withHistory: false,
|
|
110
|
-
} );
|
|
111
|
-
}
|
|
@@ -1,114 +0,0 @@
|
|
|
1
|
-
import { type V1Document } from '@elementor/editor-documents';
|
|
2
|
-
import { createElement, selectElement, type V1Element } from '@elementor/editor-elements';
|
|
3
|
-
import { registerDataHook } from '@elementor/editor-v1-adapters';
|
|
4
|
-
|
|
5
|
-
import { COMPONENT_DOCUMENT_TYPE } from '../consts';
|
|
6
|
-
import { isEditingComponent } from '../utils/is-editing-component';
|
|
7
|
-
|
|
8
|
-
const V4_DEFAULT_CONTAINER_TYPE = 'e-flexbox';
|
|
9
|
-
|
|
10
|
-
type Container = Omit< V1Element, 'children' | 'parent' > & {
|
|
11
|
-
document?: V1Document;
|
|
12
|
-
parent?: Container;
|
|
13
|
-
children?: Container[];
|
|
14
|
-
};
|
|
15
|
-
|
|
16
|
-
export function initHandleComponentEditModeContainer() {
|
|
17
|
-
initRedirectDropIntoComponent();
|
|
18
|
-
initHandleTopLevelElementDelete();
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export type DeleteArgs = {
|
|
22
|
-
container?: Container;
|
|
23
|
-
containers?: Container[];
|
|
24
|
-
};
|
|
25
|
-
|
|
26
|
-
function initHandleTopLevelElementDelete() {
|
|
27
|
-
registerDataHook( 'after', 'document/elements/delete', ( args: DeleteArgs ) => {
|
|
28
|
-
if ( ! isEditingComponent() ) {
|
|
29
|
-
return;
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
const containers = args.containers ?? ( args.container ? [ args.container ] : [] );
|
|
33
|
-
|
|
34
|
-
for ( const container of containers ) {
|
|
35
|
-
if ( ! container.parent || ! isComponent( container.parent ) ) {
|
|
36
|
-
continue;
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
const component = container.parent;
|
|
40
|
-
const isComponentEmpty = component.children?.length === 0;
|
|
41
|
-
|
|
42
|
-
if ( isComponentEmpty ) {
|
|
43
|
-
createEmptyTopLevelContainer( container.parent );
|
|
44
|
-
}
|
|
45
|
-
}
|
|
46
|
-
} );
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
type DropArgs = {
|
|
50
|
-
container?: Container;
|
|
51
|
-
containers?: Container[];
|
|
52
|
-
model?: unknown;
|
|
53
|
-
options?: unknown;
|
|
54
|
-
};
|
|
55
|
-
|
|
56
|
-
function initRedirectDropIntoComponent() {
|
|
57
|
-
registerDataHook( 'dependency', 'preview/drop', ( args: DropArgs ) => {
|
|
58
|
-
if ( ! isEditingComponent() ) {
|
|
59
|
-
return true;
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
const containers = args.containers ?? ( args.container ? [ args.container ] : [] );
|
|
63
|
-
|
|
64
|
-
for ( const container of containers ) {
|
|
65
|
-
if ( ! isComponent( container ) ) {
|
|
66
|
-
continue;
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
const { shouldRedirect, container: redirectedContainer } = getComponentContainer( container );
|
|
70
|
-
|
|
71
|
-
if ( ! shouldRedirect ) {
|
|
72
|
-
continue;
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
if ( args.containers ) {
|
|
76
|
-
const index = args.containers.indexOf( container );
|
|
77
|
-
args.containers[ index ] = redirectedContainer;
|
|
78
|
-
} else {
|
|
79
|
-
args.container = redirectedContainer;
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
return true;
|
|
84
|
-
} );
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
function createEmptyTopLevelContainer( container: Container ) {
|
|
88
|
-
const newContainer = createElement( {
|
|
89
|
-
container,
|
|
90
|
-
model: { elType: V4_DEFAULT_CONTAINER_TYPE },
|
|
91
|
-
} );
|
|
92
|
-
|
|
93
|
-
selectElement( newContainer.id );
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
function getComponentContainer( container: Container ): { shouldRedirect: boolean; container: Container } {
|
|
97
|
-
const topLevelElement = container.children?.[ 0 ];
|
|
98
|
-
|
|
99
|
-
if ( topLevelElement ) {
|
|
100
|
-
return { shouldRedirect: true, container: topLevelElement };
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
return { shouldRedirect: false, container };
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
function isComponent( container: Container ): boolean {
|
|
107
|
-
const isDocument = container.id === 'document';
|
|
108
|
-
|
|
109
|
-
if ( ! isDocument ) {
|
|
110
|
-
return false;
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
return container.document?.config.type === COMPONENT_DOCUMENT_TYPE;
|
|
114
|
-
}
|