From 1d0bf57894200edc6b9a883a41937f7a3141074f Mon Sep 17 00:00:00 2001 From: Chris Villa Date: Mon, 26 Feb 2024 23:01:53 +0100 Subject: [PATCH] feat: add iframe support --- packages/core/components/Draggable/index.tsx | 2 +- .../components/DraggableComponent/index.tsx | 2 +- .../DraggableComponent/styles.module.css | 5 +- packages/core/components/Drawer/index.tsx | 2 +- packages/core/components/DropZone/context.tsx | 2 +- packages/core/components/DropZone/index.tsx | 2 +- .../InputOrGroup/fields/ArrayField/index.tsx | 4 +- packages/core/components/LayerTree/index.tsx | 12 +++- .../Puck/components/Preview/index.tsx | 26 +++++++-- .../Puck/components/Preview/styles.module.css | 9 +++ packages/core/components/Puck/index.tsx | 10 +--- .../core/components/Puck/styles.module.css | 1 + packages/core/lib/use-placeholder-style.ts | 13 ++++- packages/core/package.json | 3 +- .../src/HeadingAnalyzer.tsx | 24 ++++++-- yarn.lock | 55 ++++++++++++++----- 16 files changed, 125 insertions(+), 47 deletions(-) create mode 100644 packages/core/components/Puck/components/Preview/styles.module.css diff --git a/packages/core/components/Draggable/index.tsx b/packages/core/components/Draggable/index.tsx index 05c36fe9e2..5ae7f1c57b 100644 --- a/packages/core/components/Draggable/index.tsx +++ b/packages/core/components/Draggable/index.tsx @@ -3,7 +3,7 @@ import { Draggable as DndDraggable, DraggableProvided, DraggableStateSnapshot, -} from "@hello-pangea/dnd"; +} from "@measured/dnd"; export const Draggable = ({ className, diff --git a/packages/core/components/DraggableComponent/index.tsx b/packages/core/components/DraggableComponent/index.tsx index 57f11c61e5..879d5e9f92 100644 --- a/packages/core/components/DraggableComponent/index.tsx +++ b/packages/core/components/DraggableComponent/index.tsx @@ -1,5 +1,5 @@ import { CSSProperties, ReactNode, SyntheticEvent, useEffect } from "react"; -import { Draggable } from "@hello-pangea/dnd"; +import { Draggable } from "@measured/dnd"; import styles from "./styles.module.css"; import getClassNameFactory from "../../lib/get-class-name-factory"; import { Copy, Trash } from "lucide-react"; diff --git a/packages/core/components/DraggableComponent/styles.module.css b/packages/core/components/DraggableComponent/styles.module.css index f2003064d4..97b7972a47 100644 --- a/packages/core/components/DraggableComponent/styles.module.css +++ b/packages/core/components/DraggableComponent/styles.module.css @@ -1,5 +1,5 @@ .DraggableComponent { - outline-offset: 0px !important; + outline-offset: -1px; pointer-events: auto; } @@ -69,6 +69,7 @@ .DraggableComponent:not(.DraggableComponent--isSelected) > .DraggableComponent-overlay { outline: 2px var(--puck-color-azure-09) solid !important; + outline-offset: -2px; } .DraggableComponent--indicativeHover > .DraggableComponent-overlay { @@ -132,7 +133,7 @@ padding-left: 8px; padding-right: 16px; margin-right: 8px; - border-right: 1px solid var(--puck-color-grey-05); + border-right: 2px solid var(--puck-color-grey-05); text-overflow: ellipsis; white-space: nowrap; } diff --git a/packages/core/components/Drawer/index.tsx b/packages/core/components/Drawer/index.tsx index a52672ccf3..db554eb19b 100644 --- a/packages/core/components/Drawer/index.tsx +++ b/packages/core/components/Drawer/index.tsx @@ -1,4 +1,4 @@ -import { Droppable } from "@hello-pangea/dnd"; +import { Droppable } from "@measured/dnd"; import styles from "./styles.module.css"; import getClassNameFactory from "../../lib/get-class-name-factory"; import { Draggable } from "../Draggable"; diff --git a/packages/core/components/DropZone/context.tsx b/packages/core/components/DropZone/context.tsx index 3bbeb2b396..b3fcc620df 100644 --- a/packages/core/components/DropZone/context.tsx +++ b/packages/core/components/DropZone/context.tsx @@ -6,7 +6,7 @@ import { useState, } from "react"; import { Config, Data } from "../../types/Config"; -import { DragStart, DragUpdate } from "@hello-pangea/dnd"; +import { DragStart, DragUpdate } from "@measured/dnd"; import { ItemSelector, getItem } from "../../lib/get-item"; import { PuckAction } from "../../reducer"; import { rootDroppableId } from "../../lib/root-droppable-id"; diff --git a/packages/core/components/DropZone/index.tsx b/packages/core/components/DropZone/index.tsx index ed74ca5bf9..84a1fe9543 100644 --- a/packages/core/components/DropZone/index.tsx +++ b/packages/core/components/DropZone/index.tsx @@ -1,6 +1,6 @@ import { CSSProperties, useContext, useEffect, useState } from "react"; import { DraggableComponent } from "../DraggableComponent"; -import { Droppable } from "@hello-pangea/dnd"; +import { Droppable } from "@measured/dnd"; import { getItem } from "../../lib/get-item"; import { setupZone } from "../../lib/setup-zone"; import { rootDroppableId } from "../../lib/root-droppable-id"; diff --git a/packages/core/components/InputOrGroup/fields/ArrayField/index.tsx b/packages/core/components/InputOrGroup/fields/ArrayField/index.tsx index a1d9de5659..31d416a368 100644 --- a/packages/core/components/InputOrGroup/fields/ArrayField/index.tsx +++ b/packages/core/components/InputOrGroup/fields/ArrayField/index.tsx @@ -4,8 +4,8 @@ import { List, Plus, Trash } from "lucide-react"; import { FieldLabelInternal, InputOrGroup, type InputProps } from "../.."; import { IconButton } from "../../../IconButton"; import { reorder, replace } from "../../../../lib"; -import { Droppable } from "@hello-pangea/dnd"; -import { DragDropContext } from "@hello-pangea/dnd"; +import { Droppable } from "@measured/dnd"; +import { DragDropContext } from "@measured/dnd"; import { Draggable } from "../../../Draggable"; import { useCallback, useEffect, useState } from "react"; import { DragIcon } from "../../../DragIcon"; diff --git a/packages/core/components/LayerTree/index.tsx b/packages/core/components/LayerTree/index.tsx index fff9cce4a9..91095540dc 100644 --- a/packages/core/components/LayerTree/index.tsx +++ b/packages/core/components/LayerTree/index.tsx @@ -95,8 +95,18 @@ export const LayerTree = ({ const id = zoneContent[i].props.id; + const iframe = document.querySelector( + "#preview-iframe" + ) as HTMLIFrameElement; + + if (!iframe.contentDocument) { + throw new Error( + `Preview iframe could not be found when trying to scroll to item ${id}` + ); + } + scrollIntoView( - document.querySelector( + iframe.contentDocument!.querySelector( `[data-rfd-drag-handle-draggable-id="draggable-${id}"]` ) as HTMLElement ); diff --git a/packages/core/components/Puck/components/Preview/index.tsx b/packages/core/components/Puck/components/Preview/index.tsx index 2929a8469a..50ee2cfceb 100644 --- a/packages/core/components/Puck/components/Preview/index.tsx +++ b/packages/core/components/Puck/components/Preview/index.tsx @@ -1,7 +1,12 @@ import { DropZone, dropZoneContext } from "../../../DropZone"; import { rootDroppableId } from "../../../../lib/root-droppable-id"; -import { useCallback, useContext } from "react"; +import { useCallback, useContext, useRef } from "react"; import { useAppContext } from "../../context"; +import AutoFrame from "@measured/auto-frame-component"; +import styles from "./styles.module.css"; +import { getClassNameFactory } from "../../../../lib"; + +const getClassName = getClassNameFactory("PuckPreview", styles); export const Preview = ({ id = "puck-preview" }: { id?: string }) => { const { config, dispatch, state } = useAppContext(); @@ -19,17 +24,28 @@ export const Preview = ({ id = "puck-preview" }: { id?: string }) => { const { disableZoom = false } = useContext(dropZoneContext) || {}; + const ref = useRef(null); + return (
{ dispatch({ type: "setUi", ui: { ...state.ui, itemSelector: null } }); }} - style={{ zoom: disableZoom ? 1 : 0.75 }} > - - - + +
+ + + +
+
); }; diff --git a/packages/core/components/Puck/components/Preview/styles.module.css b/packages/core/components/Puck/components/Preview/styles.module.css new file mode 100644 index 0000000000..a119cc8567 --- /dev/null +++ b/packages/core/components/Puck/components/Preview/styles.module.css @@ -0,0 +1,9 @@ +.PuckPreview { + height: 100%; +} + +.PuckPreview-iframe { + border: none; + height: 100%; + width: 100%; +} diff --git a/packages/core/components/Puck/index.tsx b/packages/core/components/Puck/index.tsx index c7d4d51159..fca6a84596 100644 --- a/packages/core/components/Puck/index.tsx +++ b/packages/core/components/Puck/index.tsx @@ -7,7 +7,7 @@ import { useReducer, useState, } from "react"; -import { DragDropContext, DragStart, DragUpdate } from "@hello-pangea/dnd"; +import { DragDropContext, DragStart, DragUpdate } from "@measured/dnd"; import type { AppState, Config, Data, UiState } from "../../types/Config"; import { Button } from "../Button"; @@ -496,14 +496,6 @@ export function Puck< - {/* Fill empty space under root */} -
{ const queryAttr = "data-rfd-drag-handle-draggable-id"; @@ -16,13 +16,20 @@ export const usePlaceholderStyle = () => { .droppableId; const domQuery = `[${queryAttr}='${draggableId}']`; - const draggedDOM = document.querySelector(domQuery); + + const iframe = document.querySelector( + `#preview-iframe` + ) as HTMLIFrameElement; + + const draggedDOM = + document.querySelector(domQuery) || + iframe.contentWindow?.document.querySelector(domQuery); if (!draggedDOM) { return; } - const targetListElement = document.querySelector( + const targetListElement = iframe.contentWindow?.document.querySelector( `[data-rfd-droppable-id='${droppableId}']` ); diff --git a/packages/core/package.json b/packages/core/package.json index 01b155d6e8..20020f252f 100644 --- a/packages/core/package.json +++ b/packages/core/package.json @@ -58,7 +58,8 @@ "typescript": "^4.5.2" }, "dependencies": { - "@hello-pangea/dnd": "^16.3.0", + "@measured/auto-frame-component": "0.1.0-canary.4686711", + "@measured/dnd": "16.6.0-canary.d4e2c53", "deep-diff": "^1.0.2", "react-hotkeys-hook": "^4.4.1", "react-spinners": "^0.13.8", diff --git a/packages/plugin-heading-analyzer/src/HeadingAnalyzer.tsx b/packages/plugin-heading-analyzer/src/HeadingAnalyzer.tsx index c38e287f62..066296a318 100644 --- a/packages/plugin-heading-analyzer/src/HeadingAnalyzer.tsx +++ b/packages/plugin-heading-analyzer/src/HeadingAnalyzer.tsx @@ -14,9 +14,15 @@ const dataAttr = "data-puck-heading-analyzer-id"; const getOutline = ({ addDataAttr = false, }: { addDataAttr?: boolean } = {}) => { - const headings = window.document - .querySelector("#puck-preview")! - .querySelectorAll("h1,h2,h3,h4,h5,h6"); + const iframe = document.querySelector("#preview-iframe") as HTMLIFrameElement; + + if (!iframe.contentDocument) { + throw new Error( + `Preview iframe could not be found when trying to analyze headings` + ); + } + + const headings = iframe.contentDocument.querySelectorAll("h1,h2,h3,h4,h5,h6"); const _outline: { rank: number; text: string; analyzeId: string }[] = []; @@ -127,7 +133,17 @@ export const HeadingAnalyzer = () => { : (e) => { e.stopPropagation(); - const el = document.querySelector( + const iframe = document.querySelector( + "#preview-iframe" + ) as HTMLIFrameElement; + + if (!iframe.contentDocument) { + throw new Error( + `plugin-heading-outline-analyzer: Preview iframe could not be found when trying to scroll to item` + ); + } + + const el = iframe.contentDocument.querySelector( `[${dataAttr}="${props.analyzeId}"]` ) as HTMLElement; diff --git a/yarn.lock b/yarn.lock index 2e92642cc0..84f1d0f363 100644 --- a/yarn.lock +++ b/yarn.lock @@ -525,7 +525,7 @@ dependencies: regenerator-runtime "^0.14.0" -"@babel/runtime@^7.12.1", "@babel/runtime@^7.22.5": +"@babel/runtime@^7.12.1": version "7.23.2" resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.23.2.tgz#062b0ac103261d68a966c4c7baf2ae3e62ec3885" integrity sha512-mM8eg4yl5D6i3lu2QKPuPH4FArvJ8KhTofbE7jwMUv9KX5mBvwPAqnV3MlyBNqdp9RyRKP6Yck8TrfYrPvX3bg== @@ -539,6 +539,13 @@ dependencies: regenerator-runtime "^0.14.0" +"@babel/runtime@^7.23.2": + version "7.24.0" + resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.24.0.tgz#584c450063ffda59697021430cb47101b085951e" + integrity sha512-Chk32uHMg6TnQdvw2e9IlqPpFX/6NLuK0Ys2PqLb7/gL5uFn9mXvK715FGLlOLQrcO4qIkNHkvPGktzzXexsFw== + dependencies: + regenerator-runtime "^0.14.0" + "@babel/template@^7.22.15", "@babel/template@^7.3.3": version "7.22.15" resolved "https://registry.yarnpkg.com/@babel/template/-/template-7.22.15.tgz#09576efc3830f0430f4548ef971dde1350ef2f38" @@ -1014,19 +1021,6 @@ dependencies: client-only "^0.0.1" -"@hello-pangea/dnd@^16.3.0": - version "16.3.0" - resolved "https://registry.yarnpkg.com/@hello-pangea/dnd/-/dnd-16.3.0.tgz#3776212f812df4e8e69c42831ec8ab7ff3a087d6" - integrity sha512-RYQ/K8shtJoyNPvFWz0gfXIK7HF3P3mL9UZFGMuHB0ljRSXVgMjVFI/FxcZmakMzw6tO7NflWLriwTNBow/4vw== - dependencies: - "@babel/runtime" "^7.22.5" - css-box-model "^1.2.1" - memoize-one "^6.0.0" - raf-schd "^4.0.3" - react-redux "^8.1.1" - redux "^4.2.1" - use-memo-one "^1.1.3" - "@humanwhocodes/config-array@^0.11.13": version "0.11.13" resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.13.tgz#075dc9684f40a531d9b26b0822153c1e832ee297" @@ -1446,6 +1440,27 @@ "@types/mdx" "^2.0.0" "@types/react" ">=16" +"@measured/auto-frame-component@0.1.0-canary.4686711": + version "0.1.0-canary.4686711" + resolved "https://registry.yarnpkg.com/@measured/auto-frame-component/-/auto-frame-component-0.1.0-canary.4686711.tgz#7ed8892507da83a1d5fb6d59ded7a3e15f9cd286" + integrity sha512-B3Q38ECW7xc4900PBLvHdEiws+rjx1BdHS+EEIBsw9kadT+4NMjdoTFB6wQKxtGEumI2A6tBa9IoX6UkecBkzQ== + dependencies: + object-hash "^3.0.0" + react-frame-component "5.2.6" + +"@measured/dnd@16.6.0-canary.d4e2c53": + version "16.6.0-canary.d4e2c53" + resolved "https://registry.yarnpkg.com/@measured/dnd/-/dnd-16.6.0-canary.d4e2c53.tgz#2e2b9864cbba3f5dca3abe6ed6875040f138fefb" + integrity sha512-awgtfe6hicGfodZny66as5XeA0XBzczuCJlrxxyc3ZqAxY+/iqYF1P3KekmAHaqPnjvvbUltLHJ/QBMRargkKg== + dependencies: + "@babel/runtime" "^7.23.2" + css-box-model "^1.2.1" + memoize-one "^6.0.0" + raf-schd "^4.0.3" + react-redux "^8.1.3" + redux "^4.2.1" + use-memo-one "^1.1.3" + "@napi-rs/simple-git-android-arm-eabi@0.1.9": version "0.1.9" resolved "https://registry.yarnpkg.com/@napi-rs/simple-git-android-arm-eabi/-/simple-git-android-arm-eabi-0.1.9.tgz#0326fbc4ffafb678bda3474018e2a24a8d2a21b6" @@ -10056,6 +10071,11 @@ object-assign@^4.0.1, object-assign@^4.1.1: resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" integrity sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg== +object-hash@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/object-hash/-/object-hash-3.0.0.tgz#73f97f753e7baffc0e2cc9d6e079079744ac82e9" + integrity sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw== + object-inspect@^1.12.3, object-inspect@^1.9.0: version "1.12.3" resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.12.3.tgz#ba62dffd67ee256c8c086dfae69e016cd1f198b9" @@ -10955,6 +10975,11 @@ react-dom@^18.2.0: loose-envify "^1.1.0" scheduler "^0.23.0" +react-frame-component@5.2.6: + version "5.2.6" + resolved "https://registry.yarnpkg.com/react-frame-component/-/react-frame-component-5.2.6.tgz#0d9991d251ff1f7177479d8f370deea06b824b79" + integrity sha512-CwkEM5VSt6nFwZ1Op8hi3JB5rPseZlmnp5CGiismVTauE6S4Jsc4TNMlT0O7Cts4WgIC3ZBAQ2p1Mm9XgLbj+w== + react-from-json@^0.8.0: version "0.8.0" resolved "https://registry.yarnpkg.com/react-from-json/-/react-from-json-0.8.0.tgz#c8e6c28a98180308be1eece3d22589a8c663d0dc" @@ -10980,7 +11005,7 @@ react-is@^18.0.0: resolved "https://registry.yarnpkg.com/react-is/-/react-is-18.2.0.tgz#199431eeaaa2e09f86427efbb4f1473edb47609b" integrity sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w== -react-redux@^8.1.1: +react-redux@^8.1.3: version "8.1.3" resolved "https://registry.yarnpkg.com/react-redux/-/react-redux-8.1.3.tgz#4fdc0462d0acb59af29a13c27ffef6f49ab4df46" integrity sha512-n0ZrutD7DaX/j9VscF+uTALI3oUPa/pO4Z3soOBIjuRn/FzVu6aehhysxZCLi6y7duMf52WNZGMl7CtuK5EnRw==