@webiny/app-website-builder 6.4.4-beta.5 → 6.4.4-beta.7

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.
@@ -0,0 +1 @@
1
+ export declare const CloneElement: () => null;
@@ -0,0 +1,17 @@
1
+ import { useEffect } from "react";
2
+ import { useDocumentEditor } from "../../DocumentEditor/index.js";
3
+ import { Commands } from "../index.js";
4
+ import { $cloneElement } from "../../editorSdk/utils/index.js";
5
+ const CloneElement = ()=>{
6
+ const editor = useDocumentEditor();
7
+ useEffect(()=>editor.registerCommandHandler(Commands.CloneElement, (payload)=>{
8
+ const newId = $cloneElement(editor, payload.id);
9
+ if (newId) editor.executeCommand(Commands.SelectElement, {
10
+ id: newId
11
+ });
12
+ }), []);
13
+ return null;
14
+ };
15
+ export { CloneElement };
16
+
17
+ //# sourceMappingURL=CloneElement.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"BaseEditor/commandHandlers/CloneElement.js","sources":["../../../src/BaseEditor/commandHandlers/CloneElement.tsx"],"sourcesContent":["import { useEffect } from \"react\";\nimport { useDocumentEditor } from \"~/DocumentEditor/index.js\";\nimport { Commands } from \"~/BaseEditor/index.js\";\nimport { $cloneElement } from \"~/editorSdk/utils/index.js\";\n\nexport const CloneElement = () => {\n const editor = useDocumentEditor();\n\n useEffect(() => {\n return editor.registerCommandHandler(Commands.CloneElement, payload => {\n const newId = $cloneElement(editor, payload.id);\n if (newId) {\n editor.executeCommand(Commands.SelectElement, { id: newId });\n }\n });\n }, []);\n\n return null;\n};\n"],"names":["CloneElement","editor","useDocumentEditor","useEffect","Commands","payload","newId","$cloneElement"],"mappings":";;;;AAKO,MAAMA,eAAe;IACxB,MAAMC,SAASC;IAEfC,UAAU,IACCF,OAAO,sBAAsB,CAACG,SAAS,YAAY,EAAEC,CAAAA;YACxD,MAAMC,QAAQC,cAAcN,QAAQI,QAAQ,EAAE;YAC9C,IAAIC,OACAL,OAAO,cAAc,CAACG,SAAS,aAAa,EAAE;gBAAE,IAAIE;YAAM;QAElE,IACD,EAAE;IAEL,OAAO;AACX"}
@@ -1,11 +1,12 @@
1
1
  import react from "react";
2
+ import { CloneElement } from "./CloneElement.js";
2
3
  import { CreateElement } from "./CreateElement.js";
3
4
  import { DeleteElement } from "./DeleteElement.js";
4
5
  import { MoveElement } from "./MoveElement.js";
5
6
  import { DeselectElement } from "./DeselectElement.js";
6
7
  import { SelectElement } from "./SelectElement.js";
7
8
  import { HighlightElement } from "./HighlightElement.js";
8
- const CommandHandlers = /*#__PURE__*/ react.memo(()=>/*#__PURE__*/ react.createElement(react.Fragment, null, /*#__PURE__*/ react.createElement(CreateElement, null), /*#__PURE__*/ react.createElement(DeleteElement, null), /*#__PURE__*/ react.createElement(MoveElement, null), /*#__PURE__*/ react.createElement(DeselectElement, null), /*#__PURE__*/ react.createElement(SelectElement, null), /*#__PURE__*/ react.createElement(HighlightElement, null)));
9
+ const CommandHandlers = /*#__PURE__*/ react.memo(()=>/*#__PURE__*/ react.createElement(react.Fragment, null, /*#__PURE__*/ react.createElement(CloneElement, null), /*#__PURE__*/ react.createElement(CreateElement, null), /*#__PURE__*/ react.createElement(DeleteElement, null), /*#__PURE__*/ react.createElement(MoveElement, null), /*#__PURE__*/ react.createElement(DeselectElement, null), /*#__PURE__*/ react.createElement(SelectElement, null), /*#__PURE__*/ react.createElement(HighlightElement, null)));
9
10
  CommandHandlers.displayName = "CommandHandlers";
10
11
  export { CommandHandlers };
11
12
 
@@ -1 +1 @@
1
- {"version":3,"file":"BaseEditor/commandHandlers/index.js","sources":["../../../src/BaseEditor/commandHandlers/index.tsx"],"sourcesContent":["import React from \"react\";\nimport { CreateElement } from \"./CreateElement.js\";\nimport { DeleteElement } from \"./DeleteElement.js\";\nimport { MoveElement } from \"./MoveElement.js\";\nimport { DeselectElement } from \"./DeselectElement.js\";\nimport { SelectElement } from \"./SelectElement.js\";\nimport { HighlightElement } from \"./HighlightElement.js\";\n\nexport const CommandHandlers = React.memo(() => {\n return (\n <>\n <CreateElement />\n <DeleteElement />\n <MoveElement />\n <DeselectElement />\n <SelectElement />\n <HighlightElement />\n </>\n );\n});\n\nCommandHandlers.displayName = \"CommandHandlers\";\n"],"names":["CommandHandlers","React","CreateElement","DeleteElement","MoveElement","DeselectElement","SelectElement","HighlightElement"],"mappings":";;;;;;;AAQO,MAAMA,kBAAkB,WAAHA,GAAGC,MAAAA,IAAU,CAAC,IAC/B,WAAP,GACI,wDACI,oBAACC,eAAaA,OAAAA,WAAAA,GACd,oBAACC,eAAaA,OAAAA,WAAAA,GACd,oBAACC,aAAWA,OAAAA,WAAAA,GACZ,oBAACC,iBAAeA,OAAAA,WAAAA,GAChB,oBAACC,eAAaA,OAAAA,WAAAA,GACd,oBAACC,kBAAgBA;AAK7BP,gBAAgB,WAAW,GAAG"}
1
+ {"version":3,"file":"BaseEditor/commandHandlers/index.js","sources":["../../../src/BaseEditor/commandHandlers/index.tsx"],"sourcesContent":["import React from \"react\";\nimport { CloneElement } from \"./CloneElement.js\";\nimport { CreateElement } from \"./CreateElement.js\";\nimport { DeleteElement } from \"./DeleteElement.js\";\nimport { MoveElement } from \"./MoveElement.js\";\nimport { DeselectElement } from \"./DeselectElement.js\";\nimport { SelectElement } from \"./SelectElement.js\";\nimport { HighlightElement } from \"./HighlightElement.js\";\n\nexport const CommandHandlers = React.memo(() => {\n return (\n <>\n <CloneElement />\n <CreateElement />\n <DeleteElement />\n <MoveElement />\n <DeselectElement />\n <SelectElement />\n <HighlightElement />\n </>\n );\n});\n\nCommandHandlers.displayName = \"CommandHandlers\";\n"],"names":["CommandHandlers","React","CloneElement","CreateElement","DeleteElement","MoveElement","DeselectElement","SelectElement","HighlightElement"],"mappings":";;;;;;;;AASO,MAAMA,kBAAkB,WAAHA,GAAGC,MAAAA,IAAU,CAAC,IAC/B,WAAP,GACI,wDACI,oBAACC,cAAYA,OAAAA,WAAAA,GACb,oBAACC,eAAaA,OAAAA,WAAAA,GACd,oBAACC,eAAaA,OAAAA,WAAAA,GACd,oBAACC,aAAWA,OAAAA,WAAAA,GACZ,oBAACC,iBAAeA,OAAAA,WAAAA,GAChB,oBAACC,eAAaA,OAAAA,WAAAA,GACd,oBAACC,kBAAgBA;AAK7BR,gBAAgB,WAAW,GAAG"}
@@ -1,6 +1,9 @@
1
1
  import type { ElementFactoryCreateElementParams } from "@webiny/website-builder-sdk";
2
2
  import type { WebsiteBuilderTheme } from "@webiny/website-builder-sdk/types/WebsiteBuilderTheme.js";
3
3
  export declare const Commands: {
4
+ CloneElement: import("~/editorSdk/createCommand.js").Command<{
5
+ id: string;
6
+ }>;
4
7
  CreateElement: import("~/editorSdk/createCommand.js").Command<{
5
8
  componentName: string;
6
9
  parentId: string;
@@ -1,6 +1,7 @@
1
1
  import { createCommand } from "../editorSdk/createCommand.js";
2
2
  const CreateElement = createCommand("CREATE_ELEMENT");
3
3
  const MoveElement = createCommand("MOVE_ELEMENT");
4
+ const CloneElement = createCommand("CLONE_ELEMENT");
4
5
  const DeleteElement = createCommand("DELETE_ELEMENT");
5
6
  const SelectElement = createCommand("SELECT_ELEMENT");
6
7
  const HighlightElement = createCommand("HIGHLIGHT_ELEMENT");
@@ -10,6 +11,7 @@ const RefreshPreview = createCommand("REFRESH_PREVIEW");
10
11
  const PreviewPatchElement = createCommand("PREVIEW_PATCH_ELEMENT");
11
12
  const SendPreviewMessage = createCommand("SEND_PREVIEW_MESSAGE");
12
13
  const Commands = {
14
+ CloneElement: CloneElement,
13
15
  CreateElement: CreateElement,
14
16
  DeleteElement: DeleteElement,
15
17
  MoveElement: MoveElement,
@@ -1 +1 @@
1
- {"version":3,"file":"BaseEditor/commands.js","sources":["../../src/BaseEditor/commands.ts"],"sourcesContent":["import { createCommand } from \"~/editorSdk/createCommand.js\";\nimport type { ElementFactoryCreateElementParams } from \"@webiny/website-builder-sdk\";\nimport type { WebsiteBuilderTheme } from \"@webiny/website-builder-sdk/types/WebsiteBuilderTheme.js\";\n\nconst CreateElement = createCommand<{\n // Name of the component to use.\n componentName: string;\n // Parent element for the new element.\n parentId: string;\n // Parent element slot (e.g., `children`, `heroBanner`, `tabsList.0.content`).\n slot: string;\n // Index within the slot. Omit to append at the end.\n index?: number;\n // Bindings\n bindings?: ElementFactoryCreateElementParams[\"bindings\"];\n}>(\"CREATE_ELEMENT\");\n\nconst MoveElement = createCommand<{\n // ID of the element to move.\n elementId: string;\n // Parent element for the new element.\n parentId: string;\n // Parent element slot (e.g., `children`, `heroBanner`, `tabsList.0.content`).\n slot: string;\n // Index within the slot.\n index: number;\n}>(\"MOVE_ELEMENT\");\n\nconst DeleteElement = createCommand<{\n id: string;\n}>(\"DELETE_ELEMENT\");\n\nconst SelectElement = createCommand<{ id: string }>(\"SELECT_ELEMENT\");\n\nconst HighlightElement = createCommand<{ id: string }>(\"HIGHLIGHT_ELEMENT\");\n\nconst SetTheme = createCommand<{ theme: WebsiteBuilderTheme }>(\"SET_THEME\");\n\nconst DeselectElement = createCommand<never>(\"DESELECT_ELEMENT\");\n\nconst RefreshPreview = createCommand<never>(\"REFRESH_PREVIEW\");\n\nconst PreviewPatchElement = createCommand<{ elementId: string; patch: any[] }>(\n \"PREVIEW_PATCH_ELEMENT\"\n);\n\nconst SendPreviewMessage = createCommand<{ type: string; payload?: any }>(\"SEND_PREVIEW_MESSAGE\");\n\nexport const Commands = {\n CreateElement,\n DeleteElement,\n MoveElement,\n SelectElement,\n DeselectElement,\n HighlightElement,\n RefreshPreview,\n PreviewPatchElement,\n SendPreviewMessage,\n SetTheme\n};\n"],"names":["CreateElement","createCommand","MoveElement","DeleteElement","SelectElement","HighlightElement","SetTheme","DeselectElement","RefreshPreview","PreviewPatchElement","SendPreviewMessage","Commands"],"mappings":";AAIA,MAAMA,gBAAgBC,cAWnB;AAEH,MAAMC,cAAcD,cASjB;AAEH,MAAME,gBAAgBF,cAEnB;AAEH,MAAMG,gBAAgBH,cAA8B;AAEpD,MAAMI,mBAAmBJ,cAA8B;AAEvD,MAAMK,WAAWL,cAA8C;AAE/D,MAAMM,kBAAkBN,cAAqB;AAE7C,MAAMO,iBAAiBP,cAAqB;AAE5C,MAAMQ,sBAAsBR,cACxB;AAGJ,MAAMS,qBAAqBT,cAA+C;AAEnE,MAAMU,WAAW;IACpBX,eAAAA;IACAG,eAAAA;IACAD,aAAAA;IACAE,eAAAA;IACAG,iBAAAA;IACAF,kBAAAA;IACAG,gBAAAA;IACAC,qBAAAA;IACAC,oBAAAA;IACAJ,UAAAA;AACJ"}
1
+ {"version":3,"file":"BaseEditor/commands.js","sources":["../../src/BaseEditor/commands.ts"],"sourcesContent":["import { createCommand } from \"~/editorSdk/createCommand.js\";\nimport type { ElementFactoryCreateElementParams } from \"@webiny/website-builder-sdk\";\nimport type { WebsiteBuilderTheme } from \"@webiny/website-builder-sdk/types/WebsiteBuilderTheme.js\";\n\nconst CreateElement = createCommand<{\n // Name of the component to use.\n componentName: string;\n // Parent element for the new element.\n parentId: string;\n // Parent element slot (e.g., `children`, `heroBanner`, `tabsList.0.content`).\n slot: string;\n // Index within the slot. Omit to append at the end.\n index?: number;\n // Bindings\n bindings?: ElementFactoryCreateElementParams[\"bindings\"];\n}>(\"CREATE_ELEMENT\");\n\nconst MoveElement = createCommand<{\n // ID of the element to move.\n elementId: string;\n // Parent element for the new element.\n parentId: string;\n // Parent element slot (e.g., `children`, `heroBanner`, `tabsList.0.content`).\n slot: string;\n // Index within the slot.\n index: number;\n}>(\"MOVE_ELEMENT\");\n\nconst CloneElement = createCommand<{ id: string }>(\"CLONE_ELEMENT\");\n\nconst DeleteElement = createCommand<{\n id: string;\n}>(\"DELETE_ELEMENT\");\n\nconst SelectElement = createCommand<{ id: string }>(\"SELECT_ELEMENT\");\n\nconst HighlightElement = createCommand<{ id: string }>(\"HIGHLIGHT_ELEMENT\");\n\nconst SetTheme = createCommand<{ theme: WebsiteBuilderTheme }>(\"SET_THEME\");\n\nconst DeselectElement = createCommand<never>(\"DESELECT_ELEMENT\");\n\nconst RefreshPreview = createCommand<never>(\"REFRESH_PREVIEW\");\n\nconst PreviewPatchElement = createCommand<{ elementId: string; patch: any[] }>(\n \"PREVIEW_PATCH_ELEMENT\"\n);\n\nconst SendPreviewMessage = createCommand<{ type: string; payload?: any }>(\"SEND_PREVIEW_MESSAGE\");\n\nexport const Commands = {\n CloneElement,\n CreateElement,\n DeleteElement,\n MoveElement,\n SelectElement,\n DeselectElement,\n HighlightElement,\n RefreshPreview,\n PreviewPatchElement,\n SendPreviewMessage,\n SetTheme\n};\n"],"names":["CreateElement","createCommand","MoveElement","CloneElement","DeleteElement","SelectElement","HighlightElement","SetTheme","DeselectElement","RefreshPreview","PreviewPatchElement","SendPreviewMessage","Commands"],"mappings":";AAIA,MAAMA,gBAAgBC,cAWnB;AAEH,MAAMC,cAAcD,cASjB;AAEH,MAAME,eAAeF,cAA8B;AAEnD,MAAMG,gBAAgBH,cAEnB;AAEH,MAAMI,gBAAgBJ,cAA8B;AAEpD,MAAMK,mBAAmBL,cAA8B;AAEvD,MAAMM,WAAWN,cAA8C;AAE/D,MAAMO,kBAAkBP,cAAqB;AAE7C,MAAMQ,iBAAiBR,cAAqB;AAE5C,MAAMS,sBAAsBT,cACxB;AAGJ,MAAMU,qBAAqBV,cAA+C;AAEnE,MAAMW,WAAW;IACpBT,cAAAA;IACAH,eAAAA;IACAI,eAAAA;IACAF,aAAAA;IACAG,eAAAA;IACAG,iBAAAA;IACAF,kBAAAA;IACAG,gBAAAA;IACAC,qBAAAA;IACAC,oBAAAA;IACAJ,UAAAA;AACJ"}
@@ -10,6 +10,8 @@ import { CommandHandlers } from "../commandHandlers/index.js";
10
10
  import { ElementSettings } from "./Sidebar/ElementSettings/ElementSettings.js";
11
11
  import { ElementInputRenderers } from "./ElementInputRenderers.js";
12
12
  import { ContentPreviewConfig } from "./Content/ContentPreviewConfig.js";
13
+ import { CloneElementAction } from "./Sidebar/ElementActions/CloneElementAction.js";
14
+ import { DeleteElementAction } from "./Sidebar/ElementActions/DeleteElementAction.js";
13
15
  const { Ui: Ui } = EditorConfig;
14
16
  const ClickToActivate = ()=>/*#__PURE__*/ react.createElement(Ui.NoActiveElement, null, /*#__PURE__*/ react.createElement(SidebarEmptyState, {
15
17
  message: "Select an element in the canvas to edit properties."
@@ -44,6 +46,13 @@ const DefaultEditorConfig = /*#__PURE__*/ react.memo(()=>/*#__PURE__*/ react.cre
44
46
  name: "elementSettings",
45
47
  group: "element",
46
48
  element: /*#__PURE__*/ react.createElement(Ui.OnActiveElement, null, /*#__PURE__*/ react.createElement(ElementSettings, null))
49
+ }), /*#__PURE__*/ react.createElement(EditorConfig.ElementAction, {
50
+ name: "cloneElement",
51
+ element: /*#__PURE__*/ react.createElement(CloneElementAction, null)
52
+ }), /*#__PURE__*/ react.createElement(EditorConfig.ElementAction, {
53
+ name: "deleteElement",
54
+ element: /*#__PURE__*/ react.createElement(DeleteElementAction, null),
55
+ after: "cloneElement"
47
56
  }))));
48
57
  DefaultEditorConfig.displayName = "DefaultEditorConfig";
49
58
  export { DefaultEditorConfig };
@@ -1 +1 @@
1
- {"version":3,"file":"BaseEditor/defaultConfig/DefaultEditorConfig.js","sources":["../../../src/BaseEditor/defaultConfig/DefaultEditorConfig.tsx"],"sourcesContent":["import React from \"react\";\nimport { EditorConfig } from \"~/BaseEditor/config/index.js\";\nimport { SidebarEmptyState } from \"./Sidebar/SidebarEmptyState.js\";\nimport { StyleSettingsGroup } from \"./Sidebar/StyleSettings/StyleSettingsGroup.js\";\nimport { StyleProperties } from \"./Sidebar/StyleSettings/StyleProperties.js\";\nimport { ElementSettingsGroup } from \"./Sidebar/ElementSettings/ElementSettingsGroup.js\";\nimport { InsertElementsTab } from \"./Toolbar/InsertElements/InsertElementsTab.js\";\nimport { NavigatorTab } from \"./Toolbar/Navigator/NavigatorTab.js\";\nimport { CommandHandlers } from \"~/BaseEditor/commandHandlers/index.js\";\nimport { ElementSettings } from \"./Sidebar/ElementSettings/ElementSettings.js\";\nimport { ElementInputRenderers } from \"./ElementInputRenderers.js\";\nimport { ContentPreviewConfig } from \"./Content/ContentPreviewConfig.js\";\n\nconst { Ui } = EditorConfig;\n\nconst ClickToActivate = () => {\n return (\n <Ui.NoActiveElement>\n <SidebarEmptyState message={\"Select an element in the canvas to edit properties.\"} />\n </Ui.NoActiveElement>\n );\n};\n\nexport const DefaultEditorConfig = React.memo(() => {\n return (\n <>\n <CommandHandlers />\n <EditorConfig>\n <ElementInputRenderers />\n <ContentPreviewConfig />\n <Ui.Toolbar.Element\n name={\"insertElements\"}\n group={\"tabs\"}\n element={<InsertElementsTab />}\n />\n <Ui.Toolbar.Element name={\"navigator\"} group={\"tabs\"} element={<NavigatorTab />} />\n {/* Sidebar Groups */}\n <Ui.Sidebar.Group name={\"element\"} element={<ElementSettingsGroup />} />\n <Ui.Sidebar.Group name={\"style\"} element={<StyleSettingsGroup />} />\n {/* Style Settings Tab */}\n <Ui.Sidebar.Element\n name={\"styleSettings\"}\n group={\"style\"}\n element={\n <Ui.OnActiveElement>\n <StyleProperties />\n </Ui.OnActiveElement>\n }\n />\n <Ui.Sidebar.Element\n name={\"styleInactive\"}\n group={\"style\"}\n element={<ClickToActivate />}\n />\n {/* Element Settings Tab */}\n <Ui.Sidebar.Element\n name={\"elementInactive\"}\n group={\"element\"}\n element={<ClickToActivate />}\n />\n {/* This element renders element properties. */}\n <Ui.Sidebar.Element\n name={\"elementSettings\"}\n group={\"element\"}\n element={\n <Ui.OnActiveElement>\n <ElementSettings />\n </Ui.OnActiveElement>\n }\n />\n {/*<Ui.Sidebar.Element\n name={\"stateEditor\"}\n group={\"element\"}\n element={<DocumentStateEditor />}\n />*/}\n </EditorConfig>\n </>\n );\n});\n\nDefaultEditorConfig.displayName = \"DefaultEditorConfig\";\n"],"names":["Ui","EditorConfig","ClickToActivate","SidebarEmptyState","DefaultEditorConfig","React","CommandHandlers","ElementInputRenderers","ContentPreviewConfig","InsertElementsTab","NavigatorTab","ElementSettingsGroup","StyleSettingsGroup","StyleProperties","ElementSettings"],"mappings":";;;;;;;;;;;;AAaA,MAAM,EAAEA,IAAAA,EAAE,EAAE,GAAGC;AAEf,MAAMC,kBAAkB,IACb,WAAP,GACI,oBAACF,GAAG,eAAe,sBACf,oBAACG,mBAAiBA;QAAC,SAAS;;AAKjC,MAAMC,sBAAsB,WAAHA,GAAGC,MAAAA,IAAU,CAAC,IACnC,WAAP,GACI,wDACI,oBAACC,iBAAeA,OAAAA,WAAAA,GAChB,oBAACL,cAAYA,MAAAA,WAAAA,GACT,oBAACM,uBAAqBA,OAAAA,WAAAA,GACtB,oBAACC,sBAAoBA,OAAAA,WAAAA,GACrB,oBAACR,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBAAS,oBAACS,mBAAiBA;sBAE/B,oBAACT,GAAG,OAAO,CAAC,OAAO;QAAC,MAAM;QAAa,OAAO;QAAQ,uBAAS,oBAACU,cAAYA;sBAE5E,oBAACV,GAAG,OAAO,CAAC,KAAK;QAAC,MAAM;QAAW,uBAAS,oBAACW,sBAAoBA;sBACjE,oBAACX,GAAG,OAAO,CAAC,KAAK;QAAC,MAAM;QAAS,uBAAS,oBAACY,oBAAkBA;sBAE7D,oBAACZ,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBACI,oBAACA,GAAG,eAAe,sBACf,oBAACa,iBAAeA;sBAI5B,oBAACb,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBAAS,oBAACE,iBAAeA;sBAG7B,oBAACF,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBAAS,oBAACE,iBAAeA;sBAG7B,oBAACF,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBACI,oBAACA,GAAG,eAAe,sBACf,oBAACc,iBAAeA;;AAc5CV,oBAAoB,WAAW,GAAG"}
1
+ {"version":3,"file":"BaseEditor/defaultConfig/DefaultEditorConfig.js","sources":["../../../src/BaseEditor/defaultConfig/DefaultEditorConfig.tsx"],"sourcesContent":["import React from \"react\";\nimport { EditorConfig } from \"~/BaseEditor/config/index.js\";\nimport { SidebarEmptyState } from \"./Sidebar/SidebarEmptyState.js\";\nimport { StyleSettingsGroup } from \"./Sidebar/StyleSettings/StyleSettingsGroup.js\";\nimport { StyleProperties } from \"./Sidebar/StyleSettings/StyleProperties.js\";\nimport { ElementSettingsGroup } from \"./Sidebar/ElementSettings/ElementSettingsGroup.js\";\nimport { InsertElementsTab } from \"./Toolbar/InsertElements/InsertElementsTab.js\";\nimport { NavigatorTab } from \"./Toolbar/Navigator/NavigatorTab.js\";\nimport { CommandHandlers } from \"~/BaseEditor/commandHandlers/index.js\";\nimport { ElementSettings } from \"./Sidebar/ElementSettings/ElementSettings.js\";\nimport { ElementInputRenderers } from \"./ElementInputRenderers.js\";\nimport { ContentPreviewConfig } from \"./Content/ContentPreviewConfig.js\";\nimport { CloneElementAction } from \"./Sidebar/ElementActions/CloneElementAction.js\";\nimport { DeleteElementAction } from \"./Sidebar/ElementActions/DeleteElementAction.js\";\n\nconst { Ui } = EditorConfig;\n\nconst ClickToActivate = () => {\n return (\n <Ui.NoActiveElement>\n <SidebarEmptyState message={\"Select an element in the canvas to edit properties.\"} />\n </Ui.NoActiveElement>\n );\n};\n\nexport const DefaultEditorConfig = React.memo(() => {\n return (\n <>\n <CommandHandlers />\n <EditorConfig>\n <ElementInputRenderers />\n <ContentPreviewConfig />\n <Ui.Toolbar.Element\n name={\"insertElements\"}\n group={\"tabs\"}\n element={<InsertElementsTab />}\n />\n <Ui.Toolbar.Element name={\"navigator\"} group={\"tabs\"} element={<NavigatorTab />} />\n {/* Sidebar Groups */}\n <Ui.Sidebar.Group name={\"element\"} element={<ElementSettingsGroup />} />\n <Ui.Sidebar.Group name={\"style\"} element={<StyleSettingsGroup />} />\n {/* Style Settings Tab */}\n <Ui.Sidebar.Element\n name={\"styleSettings\"}\n group={\"style\"}\n element={\n <Ui.OnActiveElement>\n <StyleProperties />\n </Ui.OnActiveElement>\n }\n />\n <Ui.Sidebar.Element\n name={\"styleInactive\"}\n group={\"style\"}\n element={<ClickToActivate />}\n />\n {/* Element Settings Tab */}\n <Ui.Sidebar.Element\n name={\"elementInactive\"}\n group={\"element\"}\n element={<ClickToActivate />}\n />\n {/* This element renders element properties. */}\n <Ui.Sidebar.Element\n name={\"elementSettings\"}\n group={\"element\"}\n element={\n <Ui.OnActiveElement>\n <ElementSettings />\n </Ui.OnActiveElement>\n }\n />\n {/*<Ui.Sidebar.Element\n name={\"stateEditor\"}\n group={\"element\"}\n element={<DocumentStateEditor />}\n />*/}\n {/* Element Actions (dropdown menu items) */}\n <EditorConfig.ElementAction\n name={\"cloneElement\"}\n element={<CloneElementAction />}\n />\n <EditorConfig.ElementAction\n name={\"deleteElement\"}\n element={<DeleteElementAction />}\n after={\"cloneElement\"}\n />\n </EditorConfig>\n </>\n );\n});\n\nDefaultEditorConfig.displayName = \"DefaultEditorConfig\";\n"],"names":["Ui","EditorConfig","ClickToActivate","SidebarEmptyState","DefaultEditorConfig","React","CommandHandlers","ElementInputRenderers","ContentPreviewConfig","InsertElementsTab","NavigatorTab","ElementSettingsGroup","StyleSettingsGroup","StyleProperties","ElementSettings","CloneElementAction","DeleteElementAction"],"mappings":";;;;;;;;;;;;;;AAeA,MAAM,EAAEA,IAAAA,EAAE,EAAE,GAAGC;AAEf,MAAMC,kBAAkB,IACb,WAAP,GACI,oBAACF,GAAG,eAAe,sBACf,oBAACG,mBAAiBA;QAAC,SAAS;;AAKjC,MAAMC,sBAAsB,WAAHA,GAAGC,MAAAA,IAAU,CAAC,IACnC,WAAP,GACI,wDACI,oBAACC,iBAAeA,OAAAA,WAAAA,GAChB,oBAACL,cAAYA,MAAAA,WAAAA,GACT,oBAACM,uBAAqBA,OAAAA,WAAAA,GACtB,oBAACC,sBAAoBA,OAAAA,WAAAA,GACrB,oBAACR,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBAAS,oBAACS,mBAAiBA;sBAE/B,oBAACT,GAAG,OAAO,CAAC,OAAO;QAAC,MAAM;QAAa,OAAO;QAAQ,uBAAS,oBAACU,cAAYA;sBAE5E,oBAACV,GAAG,OAAO,CAAC,KAAK;QAAC,MAAM;QAAW,uBAAS,oBAACW,sBAAoBA;sBACjE,oBAACX,GAAG,OAAO,CAAC,KAAK;QAAC,MAAM;QAAS,uBAAS,oBAACY,oBAAkBA;sBAE7D,oBAACZ,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBACI,oBAACA,GAAG,eAAe,sBACf,oBAACa,iBAAeA;sBAI5B,oBAACb,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBAAS,oBAACE,iBAAeA;sBAG7B,oBAACF,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBAAS,oBAACE,iBAAeA;sBAG7B,oBAACF,GAAG,OAAO,CAAC,OAAO;QACf,MAAM;QACN,OAAO;QACP,uBACI,oBAACA,GAAG,eAAe,sBACf,oBAACc,iBAAeA;sBAU5B,oBAACb,aAAa,aAAa;QACvB,MAAM;QACN,uBAAS,oBAACc,oBAAkBA;sBAEhC,oBAACd,aAAa,aAAa;QACvB,MAAM;QACN,uBAAS,oBAACe,qBAAmBA;QAC7B,OAAO;;AAO3BZ,oBAAoB,WAAW,GAAG"}
@@ -0,0 +1,2 @@
1
+ import React from "react";
2
+ export declare const CloneElementAction: () => React.JSX.Element;
@@ -0,0 +1,25 @@
1
+ import react, { useCallback } from "react";
2
+ import { DropdownMenu } from "@webiny/admin-ui";
3
+ import { ReactComponent } from "@webiny/icons/content_copy.svg";
4
+ import { useActiveElement } from "../../../hooks/useActiveElement.js";
5
+ import { useDocumentEditor } from "../../../../DocumentEditor/index.js";
6
+ import { Commands } from "../../../index.js";
7
+ const CloneElementAction = ()=>{
8
+ const [element] = useActiveElement();
9
+ const editor = useDocumentEditor();
10
+ const onClick = useCallback(()=>{
11
+ if (element) editor.executeCommand(Commands.CloneElement, {
12
+ id: element.id
13
+ });
14
+ }, [
15
+ element?.id
16
+ ]);
17
+ return /*#__PURE__*/ react.createElement(DropdownMenu.Item, {
18
+ icon: /*#__PURE__*/ react.createElement(ReactComponent, null),
19
+ text: "Clone",
20
+ onClick: onClick
21
+ });
22
+ };
23
+ export { CloneElementAction };
24
+
25
+ //# sourceMappingURL=CloneElementAction.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"BaseEditor/defaultConfig/Sidebar/ElementActions/CloneElementAction.js","sources":["../../../../../src/BaseEditor/defaultConfig/Sidebar/ElementActions/CloneElementAction.tsx"],"sourcesContent":["import React, { useCallback } from \"react\";\nimport { DropdownMenu } from \"@webiny/admin-ui\";\nimport { ReactComponent as ContentCopyIcon } from \"@webiny/icons/content_copy.svg\";\nimport { useActiveElement } from \"~/BaseEditor/hooks/useActiveElement.js\";\nimport { useDocumentEditor } from \"~/DocumentEditor/index.js\";\nimport { Commands } from \"~/BaseEditor/index.js\";\n\nexport const CloneElementAction = () => {\n const [element] = useActiveElement();\n const editor = useDocumentEditor();\n\n const onClick = useCallback(() => {\n if (element) {\n editor.executeCommand(Commands.CloneElement, { id: element.id });\n }\n }, [element?.id]);\n\n return <DropdownMenu.Item icon={<ContentCopyIcon />} text={\"Clone\"} onClick={onClick} />;\n};\n"],"names":["CloneElementAction","element","useActiveElement","editor","useDocumentEditor","onClick","useCallback","Commands","DropdownMenu","ContentCopyIcon"],"mappings":";;;;;;AAOO,MAAMA,qBAAqB;IAC9B,MAAM,CAACC,QAAQ,GAAGC;IAClB,MAAMC,SAASC;IAEf,MAAMC,UAAUC,YAAY;QACxB,IAAIL,SACAE,OAAO,cAAc,CAACI,SAAS,YAAY,EAAE;YAAE,IAAIN,QAAQ,EAAE;QAAC;IAEtE,GAAG;QAACA,SAAS;KAAG;IAEhB,OAAO,WAAP,GAAO,oBAACO,aAAa,IAAI;QAAC,oBAAM,oBAACC,gBAAeA;QAAK,MAAM;QAAS,SAASJ;;AACjF"}
@@ -0,0 +1,2 @@
1
+ import React from "react";
2
+ export declare const DeleteElementAction: () => React.JSX.Element;
@@ -0,0 +1,26 @@
1
+ import react, { useCallback } from "react";
2
+ import { DropdownMenu } from "@webiny/admin-ui";
3
+ import { ReactComponent } from "@webiny/icons/delete.svg";
4
+ import { useActiveElement } from "../../../hooks/useActiveElement.js";
5
+ import { useDocumentEditor } from "../../../../DocumentEditor/index.js";
6
+ import { Commands } from "../../../index.js";
7
+ const DeleteElementAction = ()=>{
8
+ const [element] = useActiveElement();
9
+ const editor = useDocumentEditor();
10
+ const onClick = useCallback(()=>{
11
+ if (element) editor.executeCommand(Commands.DeleteElement, {
12
+ id: element.id
13
+ });
14
+ }, [
15
+ element?.id
16
+ ]);
17
+ return /*#__PURE__*/ react.createElement(DropdownMenu.Item, {
18
+ className: "text-destructive-primary [&_svg]:fill-destructive",
19
+ icon: /*#__PURE__*/ react.createElement(ReactComponent, null),
20
+ text: "Delete",
21
+ onClick: onClick
22
+ });
23
+ };
24
+ export { DeleteElementAction };
25
+
26
+ //# sourceMappingURL=DeleteElementAction.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"BaseEditor/defaultConfig/Sidebar/ElementActions/DeleteElementAction.js","sources":["../../../../../src/BaseEditor/defaultConfig/Sidebar/ElementActions/DeleteElementAction.tsx"],"sourcesContent":["import React, { useCallback } from \"react\";\nimport { DropdownMenu } from \"@webiny/admin-ui\";\nimport { ReactComponent as DeleteIcon } from \"@webiny/icons/delete.svg\";\nimport { useActiveElement } from \"~/BaseEditor/hooks/useActiveElement.js\";\nimport { useDocumentEditor } from \"~/DocumentEditor/index.js\";\nimport { Commands } from \"~/BaseEditor/index.js\";\n\nexport const DeleteElementAction = () => {\n const [element] = useActiveElement();\n const editor = useDocumentEditor();\n\n const onClick = useCallback(() => {\n if (element) {\n editor.executeCommand(Commands.DeleteElement, { id: element.id });\n }\n }, [element?.id]);\n\n return (\n <DropdownMenu.Item\n className={\"text-destructive-primary [&_svg]:fill-destructive\"}\n icon={<DeleteIcon />}\n text={\"Delete\"}\n onClick={onClick}\n />\n );\n};\n"],"names":["DeleteElementAction","element","useActiveElement","editor","useDocumentEditor","onClick","useCallback","Commands","DropdownMenu","DeleteIcon"],"mappings":";;;;;;AAOO,MAAMA,sBAAsB;IAC/B,MAAM,CAACC,QAAQ,GAAGC;IAClB,MAAMC,SAASC;IAEf,MAAMC,UAAUC,YAAY;QACxB,IAAIL,SACAE,OAAO,cAAc,CAACI,SAAS,aAAa,EAAE;YAAE,IAAIN,QAAQ,EAAE;QAAC;IAEvE,GAAG;QAACA,SAAS;KAAG;IAEhB,OAAO,WAAP,GACI,oBAACO,aAAa,IAAI;QACd,WAAW;QACX,oBAAM,oBAACC,gBAAUA;QACjB,MAAM;QACN,SAASJ;;AAGrB"}
@@ -1,10 +1,14 @@
1
1
  import react from "react";
2
2
  import { useComponent } from "../../hooks/useComponent.js";
3
- import { Icon } from "@webiny/admin-ui";
3
+ import { DropdownMenu, Icon, IconButton } from "@webiny/admin-ui";
4
4
  import { InlineSvg } from "../Toolbar/InsertElements/InlineSvg.js";
5
+ import { ReactComponent } from "@webiny/icons/more_vert.svg";
6
+ import { ElementActions } from "../../config/ElementAction.js";
5
7
  const ElementPreview = ({ element })=>{
6
8
  const component = useComponent(element.component.name);
7
9
  return /*#__PURE__*/ react.createElement("div", {
10
+ className: "flex items-center justify-between"
11
+ }, /*#__PURE__*/ react.createElement("div", {
8
12
  className: "flex items-center gap-sm"
9
13
  }, /*#__PURE__*/ react.createElement("div", {
10
14
  className: "fill-accent-default"
@@ -16,7 +20,13 @@ const ElementPreview = ({ element })=>{
16
20
  label: component.label ?? element.component.name
17
21
  })), /*#__PURE__*/ react.createElement("span", {
18
22
  className: "text-md font-semibold text-neutral-primary"
19
- }, component.label ?? element.component.name));
23
+ }, component.label ?? element.component.name)), /*#__PURE__*/ react.createElement(DropdownMenu, {
24
+ trigger: /*#__PURE__*/ react.createElement(IconButton, {
25
+ variant: "ghost",
26
+ size: "sm",
27
+ icon: /*#__PURE__*/ react.createElement(ReactComponent, null)
28
+ })
29
+ }, /*#__PURE__*/ react.createElement(ElementActions, null)));
20
30
  };
21
31
  export { ElementPreview };
22
32
 
@@ -1 +1 @@
1
- {"version":3,"file":"BaseEditor/defaultConfig/Sidebar/ElementPreview.js","sources":["../../../../src/BaseEditor/defaultConfig/Sidebar/ElementPreview.tsx"],"sourcesContent":["import React from \"react\";\nimport type { DocumentElement } from \"@webiny/website-builder-sdk\";\nimport { useComponent } from \"~/BaseEditor/hooks/useComponent.js\";\nimport { Icon } from \"@webiny/admin-ui\";\nimport { InlineSvg } from \"~/BaseEditor/defaultConfig/Toolbar/InsertElements/InlineSvg.js\";\n\ninterface ElementPreviewProps {\n element: DocumentElement;\n}\n\nexport const ElementPreview = ({ element }: ElementPreviewProps) => {\n const component = useComponent(element.component.name);\n\n return (\n <div className={\"flex items-center gap-sm\"}>\n <div className={\"fill-accent-default\"}>\n {component.image && (\n <Icon\n icon={<InlineSvg src={component.image} />}\n size={\"md\"}\n label={component.label ?? element.component.name}\n />\n )}\n </div>\n <span className={\"text-md font-semibold text-neutral-primary\"}>\n {component.label ?? element.component.name}\n </span>\n </div>\n );\n};\n"],"names":["ElementPreview","element","component","useComponent","Icon","InlineSvg"],"mappings":";;;;AAUO,MAAMA,iBAAiB,CAAC,EAAEC,OAAO,EAAuB;IAC3D,MAAMC,YAAYC,aAAaF,QAAQ,SAAS,CAAC,IAAI;IAErD,OAAO,WAAP,GACI,oBAAC;QAAI,WAAW;qBACZ,oBAAC;QAAI,WAAW;OACXC,UAAU,KAAK,IAAI,WAAJ,GACZ,oBAACE,MAAIA;QACD,oBAAM,oBAACC,WAASA;YAAC,KAAKH,UAAU,KAAK;;QACrC,MAAM;QACN,OAAOA,UAAU,KAAK,IAAID,QAAQ,SAAS,CAAC,IAAI;uBAI5D,oBAAC;QAAK,WAAW;OACZC,UAAU,KAAK,IAAID,QAAQ,SAAS,CAAC,IAAI;AAI1D"}
1
+ {"version":3,"file":"BaseEditor/defaultConfig/Sidebar/ElementPreview.js","sources":["../../../../src/BaseEditor/defaultConfig/Sidebar/ElementPreview.tsx"],"sourcesContent":["import React from \"react\";\nimport type { DocumentElement } from \"@webiny/website-builder-sdk\";\nimport { useComponent } from \"~/BaseEditor/hooks/useComponent.js\";\nimport { DropdownMenu, Icon, IconButton } from \"@webiny/admin-ui\";\nimport { InlineSvg } from \"~/BaseEditor/defaultConfig/Toolbar/InsertElements/InlineSvg.js\";\nimport { ReactComponent as MoreVerticalIcon } from \"@webiny/icons/more_vert.svg\";\nimport { ElementActions } from \"~/BaseEditor/config/ElementAction.js\";\n\ninterface ElementPreviewProps {\n element: DocumentElement;\n}\n\nexport const ElementPreview = ({ element }: ElementPreviewProps) => {\n const component = useComponent(element.component.name);\n\n return (\n <div className={\"flex items-center justify-between\"}>\n <div className={\"flex items-center gap-sm\"}>\n <div className={\"fill-accent-default\"}>\n {component.image && (\n <Icon\n icon={<InlineSvg src={component.image} />}\n size={\"md\"}\n label={component.label ?? element.component.name}\n />\n )}\n </div>\n <span className={\"text-md font-semibold text-neutral-primary\"}>\n {component.label ?? element.component.name}\n </span>\n </div>\n <DropdownMenu\n trigger={<IconButton variant={\"ghost\"} size={\"sm\"} icon={<MoreVerticalIcon />} />}\n >\n <ElementActions />\n </DropdownMenu>\n </div>\n );\n};\n"],"names":["ElementPreview","element","component","useComponent","Icon","InlineSvg","DropdownMenu","IconButton","MoreVerticalIcon","ElementActions"],"mappings":";;;;;;AAYO,MAAMA,iBAAiB,CAAC,EAAEC,OAAO,EAAuB;IAC3D,MAAMC,YAAYC,aAAaF,QAAQ,SAAS,CAAC,IAAI;IAErD,OAAO,WAAP,GACI,oBAAC;QAAI,WAAW;qBACZ,oBAAC;QAAI,WAAW;qBACZ,oBAAC;QAAI,WAAW;OACXC,UAAU,KAAK,IAAI,WAAJ,GACZ,oBAACE,MAAIA;QACD,oBAAM,oBAACC,WAASA;YAAC,KAAKH,UAAU,KAAK;;QACrC,MAAM;QACN,OAAOA,UAAU,KAAK,IAAID,QAAQ,SAAS,CAAC,IAAI;uBAI5D,oBAAC;QAAK,WAAW;OACZC,UAAU,KAAK,IAAID,QAAQ,SAAS,CAAC,IAAI,kBAGlD,oBAACK,cAAYA;QACT,uBAAS,oBAACC,YAAUA;YAAC,SAAS;YAAS,MAAM;YAAM,oBAAM,oBAACC,gBAAgBA;;qBAE1E,oBAACC,gBAAcA;AAI/B"}
@@ -0,0 +1,2 @@
1
+ import type { Editor } from "../Editor.js";
2
+ export declare function $cloneElement(editor: Editor, id: string): string | undefined;
@@ -0,0 +1,112 @@
1
+ import { ElementFactory, generateElementId } from "@webiny/website-builder-sdk";
2
+ import { $getElementById } from "./$getElementById.js";
3
+ import { $addElementReferenceToParent } from "./$addElementReferenceToParent.js";
4
+ import { applyAncestorUpdates, executeOnChange } from "./executeOnChange.js";
5
+ function collectDescendants(document, elementId) {
6
+ const ids = [];
7
+ const bindings = document.bindings[elementId];
8
+ if (!bindings?.inputs) return ids;
9
+ for (const binding of Object.values(bindings.inputs)){
10
+ if ("slot" !== binding.type) continue;
11
+ const children = binding.list ? binding.static ?? [] : binding.static ? [
12
+ binding.static
13
+ ] : [];
14
+ for (const childId of children){
15
+ ids.push(childId);
16
+ ids.push(...collectDescendants(document, childId));
17
+ }
18
+ }
19
+ return ids;
20
+ }
21
+ function remapBindings(bindings, idMap) {
22
+ const cloned = structuredClone(bindings);
23
+ if (cloned.inputs) {
24
+ for (const [key, binding] of Object.entries(cloned.inputs))if ("slot" === binding.type) {
25
+ if (binding.list && Array.isArray(binding.static)) cloned.inputs[key] = {
26
+ ...binding,
27
+ static: binding.static.map((id)=>idMap.get(id) ?? id)
28
+ };
29
+ else if ("string" == typeof binding.static) {
30
+ const newId = idMap.get(binding.static);
31
+ if (newId) cloned.inputs[key] = {
32
+ ...binding,
33
+ static: newId
34
+ };
35
+ }
36
+ }
37
+ }
38
+ return cloned;
39
+ }
40
+ function getSlotIndex(document, element) {
41
+ const parent = element.parent;
42
+ if (!parent) return -1;
43
+ const parentBindings = document.bindings[parent.id];
44
+ if (!parentBindings?.inputs) return -1;
45
+ const slotBinding = parentBindings.inputs[parent.slot];
46
+ if (!slotBinding) return -1;
47
+ if (slotBinding.list && Array.isArray(slotBinding.static)) return slotBinding.static.indexOf(element.id);
48
+ return -1;
49
+ }
50
+ function $cloneElement(editor, id) {
51
+ const document = editor.getDocumentState().read();
52
+ const element = $getElementById(document, id);
53
+ if (!element || !element.parent) return;
54
+ const allIds = [
55
+ id,
56
+ ...collectDescendants(document, id)
57
+ ];
58
+ const idMap = new Map();
59
+ for (const oldId of allIds)idMap.set(oldId, generateElementId());
60
+ const originalIndex = getSlotIndex(document, element);
61
+ editor.updateDocument((doc)=>{
62
+ for (const oldId of allIds){
63
+ const original = doc.elements[oldId];
64
+ const newId = idMap.get(oldId);
65
+ const clonedElement = {
66
+ ...structuredClone(original),
67
+ id: newId
68
+ };
69
+ if (clonedElement.parent) {
70
+ const newParentId = idMap.get(clonedElement.parent.id);
71
+ if (newParentId) clonedElement.parent = {
72
+ ...clonedElement.parent,
73
+ id: newParentId
74
+ };
75
+ }
76
+ doc.elements[newId] = clonedElement;
77
+ const originalBindings = doc.bindings[oldId];
78
+ if (originalBindings) doc.bindings[newId] = remapBindings(originalBindings, idMap);
79
+ }
80
+ const rootNewId = idMap.get(id);
81
+ const insertIndex = originalIndex >= 0 ? originalIndex + 1 : originalIndex;
82
+ $addElementReferenceToParent(doc, {
83
+ elementId: rootNewId,
84
+ parentId: element.parent.id,
85
+ slot: element.parent.slot,
86
+ index: insertIndex
87
+ });
88
+ });
89
+ const componentsManifest = editor.getEditorState().read().components;
90
+ const editorState = editor.getEditorState().read();
91
+ const breakpointNames = editorState.viewport.breakpoints.map((bp)=>bp.name);
92
+ const baseBreakpoint = breakpointNames[0];
93
+ const elementFactory = new ElementFactory(componentsManifest);
94
+ for (const oldId of allIds){
95
+ const newId = idMap.get(oldId);
96
+ const ancestorUpdates = executeOnChange({
97
+ editor,
98
+ elementId: newId,
99
+ action: "create",
100
+ breakpointNames,
101
+ baseBreakpoint,
102
+ elementFactory
103
+ });
104
+ if (ancestorUpdates.length > 0) editor.updateDocument((doc)=>{
105
+ applyAncestorUpdates(doc, ancestorUpdates, breakpointNames, baseBreakpoint, elementFactory);
106
+ });
107
+ }
108
+ return idMap.get(id);
109
+ }
110
+ export { $cloneElement };
111
+
112
+ //# sourceMappingURL=$cloneElement.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"editorSdk/utils/$cloneElement.js","sources":["../../../src/editorSdk/utils/$cloneElement.ts"],"sourcesContent":["import { generateElementId } from \"@webiny/website-builder-sdk\";\nimport type {\n Document,\n DocumentElement,\n DocumentElementBindings\n} from \"@webiny/website-builder-sdk\";\nimport { ElementFactory } from \"@webiny/website-builder-sdk\";\nimport type { Editor } from \"../Editor.js\";\nimport { $getElementById } from \"./$getElementById.js\";\nimport { $addElementReferenceToParent } from \"./$addElementReferenceToParent.js\";\nimport { executeOnChange, applyAncestorUpdates } from \"./executeOnChange.js\";\n\nfunction collectDescendants(document: Document, elementId: string): string[] {\n const ids: string[] = [];\n const bindings = document.bindings[elementId];\n if (!bindings?.inputs) {\n return ids;\n }\n\n for (const binding of Object.values(bindings.inputs)) {\n if (binding.type !== \"slot\") {\n continue;\n }\n\n const children = binding.list\n ? ((binding.static as string[] | undefined) ?? [])\n : binding.static\n ? [binding.static as string]\n : [];\n\n for (const childId of children) {\n ids.push(childId);\n ids.push(...collectDescendants(document, childId));\n }\n }\n\n return ids;\n}\n\nfunction remapBindings(\n bindings: DocumentElementBindings,\n idMap: Map<string, string>\n): DocumentElementBindings {\n const cloned = structuredClone(bindings);\n\n if (cloned.inputs) {\n for (const [key, binding] of Object.entries(cloned.inputs)) {\n if (binding.type !== \"slot\") {\n continue;\n }\n\n if (binding.list && Array.isArray(binding.static)) {\n cloned.inputs[key] = {\n ...binding,\n static: binding.static.map((id: string) => idMap.get(id) ?? id)\n };\n } else if (typeof binding.static === \"string\") {\n const newId = idMap.get(binding.static);\n if (newId) {\n cloned.inputs[key] = { ...binding, static: newId };\n }\n }\n }\n }\n\n return cloned;\n}\n\nfunction getSlotIndex(document: Document, element: DocumentElement): number {\n const parent = element.parent;\n if (!parent) {\n return -1;\n }\n\n const parentBindings = document.bindings[parent.id];\n if (!parentBindings?.inputs) {\n return -1;\n }\n\n const slotBinding = parentBindings.inputs[parent.slot];\n if (!slotBinding) {\n return -1;\n }\n\n if (slotBinding.list && Array.isArray(slotBinding.static)) {\n return slotBinding.static.indexOf(element.id);\n }\n\n return -1;\n}\n\nexport function $cloneElement(editor: Editor, id: string): string | undefined {\n const document = editor.getDocumentState().read();\n const element = $getElementById(document, id);\n\n if (!element || !element.parent) {\n return undefined;\n }\n\n const allIds = [id, ...collectDescendants(document, id)];\n const idMap = new Map<string, string>();\n for (const oldId of allIds) {\n idMap.set(oldId, generateElementId());\n }\n\n const originalIndex = getSlotIndex(document, element);\n\n editor.updateDocument(doc => {\n for (const oldId of allIds) {\n const original = doc.elements[oldId];\n const newId = idMap.get(oldId)!;\n\n const clonedElement: DocumentElement = {\n ...structuredClone(original),\n id: newId\n };\n\n if (clonedElement.parent) {\n const newParentId = idMap.get(clonedElement.parent.id);\n if (newParentId) {\n clonedElement.parent = {\n ...clonedElement.parent,\n id: newParentId\n };\n }\n }\n\n doc.elements[newId] = clonedElement;\n\n const originalBindings = doc.bindings[oldId];\n if (originalBindings) {\n doc.bindings[newId] = remapBindings(originalBindings, idMap);\n }\n }\n\n const rootNewId = idMap.get(id)!;\n const insertIndex = originalIndex >= 0 ? originalIndex + 1 : originalIndex;\n\n $addElementReferenceToParent(doc, {\n elementId: rootNewId,\n parentId: element.parent!.id,\n slot: element.parent!.slot,\n index: insertIndex\n });\n });\n\n const componentsManifest = editor.getEditorState().read().components;\n const editorState = editor.getEditorState().read();\n const breakpointNames = editorState.viewport.breakpoints.map(bp => bp.name);\n const baseBreakpoint = breakpointNames[0];\n const elementFactory = new ElementFactory(componentsManifest);\n\n for (const oldId of allIds) {\n const newId = idMap.get(oldId)!;\n const ancestorUpdates = executeOnChange({\n editor,\n elementId: newId,\n action: \"create\",\n breakpointNames,\n baseBreakpoint,\n elementFactory\n });\n\n if (ancestorUpdates.length > 0) {\n editor.updateDocument(doc => {\n applyAncestorUpdates(\n doc,\n ancestorUpdates,\n breakpointNames,\n baseBreakpoint,\n elementFactory\n );\n });\n }\n }\n\n return idMap.get(id);\n}\n"],"names":["collectDescendants","document","elementId","ids","bindings","binding","Object","children","childId","remapBindings","idMap","cloned","structuredClone","key","Array","id","newId","getSlotIndex","element","parent","parentBindings","slotBinding","$cloneElement","editor","$getElementById","allIds","Map","oldId","generateElementId","originalIndex","doc","original","clonedElement","newParentId","originalBindings","rootNewId","insertIndex","$addElementReferenceToParent","componentsManifest","editorState","breakpointNames","bp","baseBreakpoint","elementFactory","ElementFactory","ancestorUpdates","executeOnChange","applyAncestorUpdates"],"mappings":"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"}
@@ -14,4 +14,5 @@ export * from "./$getFirstElementOfType.js";
14
14
  export * from "./$getElementInputValues.js";
15
15
  export * from "./$updateElementInputs.js";
16
16
  export * from "./$previewElementInputs.js";
17
+ export * from "./$cloneElement.js";
17
18
  export * from "./executeOnChange.js";
@@ -14,4 +14,5 @@ export * from "./$getFirstElementOfType.js";
14
14
  export * from "./$getElementInputValues.js";
15
15
  export * from "./$updateElementInputs.js";
16
16
  export * from "./$previewElementInputs.js";
17
+ export * from "./$cloneElement.js";
17
18
  export * from "./executeOnChange.js";
package/index.js CHANGED
@@ -1,7 +1,7 @@
1
- import * as __rspack_external__BaseEditor_index_js_b2c17421 from "./BaseEditor/index.js";
1
+ import * as __rspack_external__BaseEditor_index_js_dc6c77f1 from "./BaseEditor/index.js";
2
2
  export * from "./shared/pagePathFromTitle.js";
3
3
  export { PageListConfig } from "./modules/pages/configs/index.js";
4
4
  export { RedirectListConfig } from "./modules/redirects/configs/index.js";
5
5
  export { PageEditorConfig } from "./modules/pages/PageEditor/PageEditorConfig.js";
6
6
  export { PreviewUrlModifier } from "./features/index.js";
7
- export { __rspack_external__BaseEditor_index_js_b2c17421 as Editor };
7
+ export { __rspack_external__BaseEditor_index_js_dc6c77f1 as Editor };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@webiny/app-website-builder",
3
- "version": "6.4.4-beta.5",
3
+ "version": "6.4.4-beta.7",
4
4
  "type": "module",
5
5
  "exports": {
6
6
  ".": "./index.js",
@@ -17,32 +17,32 @@
17
17
  "@emotion/css": "11.13.5",
18
18
  "@emotion/react": "11.14.0",
19
19
  "@emotion/styled": "11.14.1",
20
- "@lexical/utils": "0.44.0",
20
+ "@lexical/utils": "0.46.0",
21
21
  "@monaco-editor/react": "4.7.0",
22
22
  "@svgr/webpack": "8.1.0",
23
- "@types/react": "18.3.29",
24
- "@webiny/admin-ui": "6.4.4-beta.5",
25
- "@webiny/app": "6.4.4-beta.5",
26
- "@webiny/app-aco": "6.4.4-beta.5",
27
- "@webiny/app-admin": "6.4.4-beta.5",
28
- "@webiny/app-headless-cms-common": "6.4.4-beta.5",
29
- "@webiny/app-trash-bin": "6.4.4-beta.5",
30
- "@webiny/app-utils": "6.4.4-beta.5",
31
- "@webiny/di": "1.0.1",
32
- "@webiny/error": "6.4.4-beta.5",
33
- "@webiny/feature": "6.4.4-beta.5",
34
- "@webiny/form": "6.4.4-beta.5",
35
- "@webiny/icons": "6.4.4-beta.5",
36
- "@webiny/languages": "6.4.4-beta.5",
37
- "@webiny/lexical-converter": "6.4.4-beta.5",
38
- "@webiny/lexical-editor": "6.4.4-beta.5",
39
- "@webiny/lexical-nodes": "6.4.4-beta.5",
40
- "@webiny/lexical-theme": "6.4.4-beta.5",
41
- "@webiny/react-composition": "6.4.4-beta.5",
42
- "@webiny/react-properties": "6.4.4-beta.5",
43
- "@webiny/utils": "6.4.4-beta.5",
44
- "@webiny/validation": "6.4.4-beta.5",
45
- "@webiny/website-builder-sdk": "6.4.4-beta.5",
23
+ "@types/react": "18.3.31",
24
+ "@webiny/admin-ui": "6.4.4-beta.7",
25
+ "@webiny/app": "6.4.4-beta.7",
26
+ "@webiny/app-aco": "6.4.4-beta.7",
27
+ "@webiny/app-admin": "6.4.4-beta.7",
28
+ "@webiny/app-headless-cms-common": "6.4.4-beta.7",
29
+ "@webiny/app-trash-bin": "6.4.4-beta.7",
30
+ "@webiny/app-utils": "6.4.4-beta.7",
31
+ "@webiny/di": "1.0.2",
32
+ "@webiny/error": "6.4.4-beta.7",
33
+ "@webiny/feature": "6.4.4-beta.7",
34
+ "@webiny/form": "6.4.4-beta.7",
35
+ "@webiny/icons": "6.4.4-beta.7",
36
+ "@webiny/languages": "6.4.4-beta.7",
37
+ "@webiny/lexical-converter": "6.4.4-beta.7",
38
+ "@webiny/lexical-editor": "6.4.4-beta.7",
39
+ "@webiny/lexical-nodes": "6.4.4-beta.7",
40
+ "@webiny/lexical-theme": "6.4.4-beta.7",
41
+ "@webiny/react-composition": "6.4.4-beta.7",
42
+ "@webiny/react-properties": "6.4.4-beta.7",
43
+ "@webiny/utils": "6.4.4-beta.7",
44
+ "@webiny/validation": "6.4.4-beta.7",
45
+ "@webiny/website-builder-sdk": "6.4.4-beta.7",
46
46
  "apollo-cache": "1.3.5",
47
47
  "apollo-client": "2.6.10",
48
48
  "apollo-link": "1.2.14",
@@ -50,7 +50,7 @@
50
50
  "classnames": "2.5.1",
51
51
  "deep-equal": "2.2.3",
52
52
  "graphql": "16.14.2",
53
- "graphql-tag": "2.12.6",
53
+ "graphql-tag": "2.12.7",
54
54
  "is-hotkey": "0.2.0",
55
55
  "lodash": "4.18.1",
56
56
  "markdown-to-jsx": "9.8.2",
@@ -58,7 +58,7 @@
58
58
  "mobx": "6.16.1",
59
59
  "mobx-react-lite": "4.1.1",
60
60
  "pluralize": "8.0.0",
61
- "radix-ui": "1.5.0",
61
+ "radix-ui": "1.6.2",
62
62
  "react": "18.3.1",
63
63
  "react-dnd": "16.0.1",
64
64
  "react-dnd-html5-backend": "16.0.1",
@@ -69,11 +69,11 @@
69
69
  "devDependencies": {
70
70
  "@types/deep-equal": "1.0.4",
71
71
  "@types/is-hotkey": "0.1.10",
72
- "@webiny/build-tools": "6.4.4-beta.5",
72
+ "@webiny/build-tools": "6.4.4-beta.7",
73
73
  "execa": "5.1.1",
74
74
  "rimraf": "6.1.3",
75
75
  "typescript": "6.0.3",
76
- "vitest": "4.1.8"
76
+ "vitest": "4.1.10"
77
77
  },
78
78
  "publishConfig": {
79
79
  "access": "public"