diff --git a/apps/builder/app/builder/features/marketplace/templates.tsx b/apps/builder/app/builder/features/marketplace/templates.tsx index 099cfdb5ee7f..4789bf30c135 100644 --- a/apps/builder/app/builder/features/marketplace/templates.tsx +++ b/apps/builder/app/builder/features/marketplace/templates.tsx @@ -12,6 +12,7 @@ import { } from "@webstudio-is/design-system"; import { ChevronLeftIcon, ExternalLinkIcon } from "@webstudio-is/icons"; import { + elementComponent, ROOT_FOLDER_ID, type Asset, type Page, @@ -50,9 +51,12 @@ const insertSection = ({ ); // remove body and use its children as root insrances if (body) { - fragment.instances = fragment.instances.filter( - (instance) => instance.component !== "Body" - ); + fragment.instances = fragment.instances.filter((instance) => { + const isBody = + instance.component === "Body" || + (instance.component === elementComponent && instance.tag === "body"); + return !isBody; + }); fragment.children = body.children; } const insertable = findClosestInsertable(fragment); diff --git a/apps/builder/app/builder/features/pages/page-settings.tsx b/apps/builder/app/builder/features/pages/page-settings.tsx index d44f22559ea4..d0c51da0a7f9 100644 --- a/apps/builder/app/builder/features/pages/page-settings.tsx +++ b/apps/builder/app/builder/features/pages/page-settings.tsx @@ -29,6 +29,7 @@ import { isLiteralExpression, documentTypes, isRootFolder, + elementComponent, } from "@webstudio-is/sdk"; import { theme, @@ -1307,7 +1308,8 @@ const createPage = (pageId: Page["id"], values: Values) => { instances.set(rootInstanceId, { type: "instance", id: rootInstanceId, - component: "Body", + component: elementComponent, + tag: "body", children: [], }); registerFolderChildMutable(pages.folders, pageId, values.parentFolderId); diff --git a/apps/builder/app/builder/features/settings-panel/controls/tag-control.tsx b/apps/builder/app/builder/features/settings-panel/controls/tag-control.tsx index 9f86a379acd8..993f0e47e37e 100644 --- a/apps/builder/app/builder/features/settings-panel/controls/tag-control.tsx +++ b/apps/builder/app/builder/features/settings-panel/controls/tag-control.tsx @@ -46,7 +46,11 @@ export const TagControl = ({ meta, prop }: ControlProps<"tag">) => { const instanceTag = instance?.tag; const defaultTag = meta.options[0]; const computedTag = instanceTag ?? propTag ?? defaultTag; - const satisfyingTags = useStore($satisfyingTags); + let satisfyingTags = useStore($satisfyingTags); + // forbid changing tag on body element + if (computedTag === "body") { + satisfyingTags = ["body"]; + } const options = meta.options.filter((tag) => satisfyingTags.includes(tag)); const [value, setValue] = useState(); const updateTag = (value: string) => { diff --git a/apps/builder/app/canvas/canvas.tsx b/apps/builder/app/canvas/canvas.tsx index 0db362e372e2..0db6362abac6 100644 --- a/apps/builder/app/canvas/canvas.tsx +++ b/apps/builder/app/canvas/canvas.tsx @@ -71,7 +71,6 @@ import { subscribeSelected } from "./instance-selected"; import { subscribeScrollNewInstanceIntoView } from "./shared/scroll-new-instance-into-view"; import { $selectedPage } from "~/shared/awareness"; import { createInstanceElement } from "./elements"; -import { Body } from "./shared/body"; import { subscribeScrollbarSize } from "./scrollbar-width"; import { compareMedia } from "@webstudio-is/css-engine"; import { builderApi } from "~/shared/builder-api"; @@ -248,15 +247,6 @@ export const Canvas = () => { hooks: baseComponentHooks, templates: baseComponentTemplates, }); - registerComponentLibrary({ - components: { - // override only canvas specific body component - // not related to sdk-components-react-remix anymore - Body, - }, - metas: {}, - templates: {}, - }); registerComponentLibrary({ namespace: "@webstudio-is/sdk-components-react-radix", components: radixComponents, @@ -321,7 +311,7 @@ export const Canvas = () => { }, []); if (components.size === 0 || instances.size === 0) { - return ; + return; } return ( diff --git a/apps/builder/app/canvas/shared/body.tsx b/apps/builder/app/canvas/shared/body.tsx deleted file mode 100644 index eb42bf45869a..000000000000 --- a/apps/builder/app/canvas/shared/body.tsx +++ /dev/null @@ -1,14 +0,0 @@ -import { forwardRef, type ElementRef, type ComponentProps } from "react"; -import { Scripts, ScrollRestoration } from "@remix-run/react"; - -export const Body = forwardRef, ComponentProps<"body">>( - ({ children, ...props }, ref) => ( - - {children} - - - - ) -); - -Body.displayName = "Body"; diff --git a/apps/builder/app/routes/_canvas.canvas.tsx b/apps/builder/app/routes/_canvas.canvas.tsx index f55679b46f07..b6f0cf3d7b49 100644 --- a/apps/builder/app/routes/_canvas.canvas.tsx +++ b/apps/builder/app/routes/_canvas.canvas.tsx @@ -1,8 +1,8 @@ import { lazy } from "react"; -import { type LoaderFunctionArgs } from "@remix-run/server-runtime"; +import type { LoaderFunctionArgs } from "@remix-run/server-runtime"; +import { Scripts, ScrollRestoration } from "@remix-run/react"; import { isCanvas } from "~/shared/router-utils"; import { ClientOnly } from "~/shared/client-only"; -import { Body } from "~/canvas/shared/body"; export { ErrorBoundary } from "~/shared/error/error-boundary"; @@ -22,7 +22,16 @@ const Canvas = lazy(async () => { const CanvasRoute = () => { return ( - }> + // this setup remix scripts on canvas and after rendering a website + // scripts will continue to work even though removed from dom + + + + + } + > ); diff --git a/packages/project-build/src/db/build.ts b/packages/project-build/src/db/build.ts index a6ef58c3ea8b..33037b0c3f09 100644 --- a/packages/project-build/src/db/build.ts +++ b/packages/project-build/src/db/build.ts @@ -20,6 +20,7 @@ import { type StyleDecl, Pages, initialBreakpoints, + elementComponent, } from "@webstudio-is/sdk"; import type { Build, CompactBuild } from "../types"; import { parseDeployment } from "./deployment"; @@ -229,7 +230,8 @@ const createNewPageInstances = (): Build["instances"] => { { type: "instance", id: instanceId, - component: "Body", + component: elementComponent, + tag: "body", children: [], }, ],