Skip to content

Commit

Permalink
fix: always respect history hotkeys inside iframes
Browse files Browse the repository at this point in the history
  • Loading branch information
chrisvxd committed Jan 10, 2025
1 parent 2d90701 commit 1134e8b
Show file tree
Hide file tree
Showing 7 changed files with 91 additions and 15 deletions.
7 changes: 6 additions & 1 deletion packages/core/components/Puck/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -246,7 +246,12 @@ export function Puck<

const { data, ui } = appState;

const history = usePuckHistory({ dispatch, initialAppState, historyStore });
const history = usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: _iframe?.enabled ?? true,
});

const [menuOpen, setMenuOpen] = useState(false);

Expand Down
49 changes: 42 additions & 7 deletions packages/core/lib/__tests__/use-puck-history.spec.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,12 @@ beforeEach(() => {
describe("use-puck-history", () => {
test("back function does not call dispatch when there is no history", () => {
const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

act(() => {
Expand All @@ -47,7 +52,12 @@ describe("use-puck-history", () => {
};

const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

act(() => {
Expand All @@ -66,7 +76,12 @@ describe("use-puck-history", () => {
historyStore.nextHistory = null;

const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

act(() => {
Expand All @@ -86,7 +101,12 @@ describe("use-puck-history", () => {
};

const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

act(() => {
Expand All @@ -102,7 +122,12 @@ describe("use-puck-history", () => {

test("setHistories calls dispatch to last history item", () => {
const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

const updatedHistories = [
Expand Down Expand Up @@ -153,7 +178,12 @@ describe("use-puck-history", () => {
historyStore.histories = updatedHistories;

const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

act(() => {
Expand All @@ -169,7 +199,12 @@ describe("use-puck-history", () => {

test("setHistoryIndex does not call dispatch when index out of bounds", () => {
const { result } = renderHook(() =>
usePuckHistory({ dispatch, initialAppState, historyStore })
usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled: false,
})
);

act(() => {
Expand Down
10 changes: 6 additions & 4 deletions packages/core/lib/get-frame.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,12 @@
export const getFrame = () => {
let frame: Element | Document | null | undefined =
if (typeof window === "undefined") return;

let frameEl: Element | Document | null | undefined =
document.querySelector("#preview-frame");

if (frame?.tagName === "IFRAME") {
frame = (frame as HTMLIFrameElement)!.contentDocument;
if (frameEl?.tagName === "IFRAME") {
return (frameEl as HTMLIFrameElement)!.contentDocument || document;
}

return frame;
return frameEl?.ownerDocument || document;
};
2 changes: 1 addition & 1 deletion packages/core/lib/use-frame.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { useEffect, useState } from "react";
import { getFrame } from "./get-frame";

export const useFrame = () => {
const [el, setEl] = useState<Element | Document>();
const [el, setEl] = useState<Document>();

useEffect(() => {
const frame = getFrame();
Expand Down
34 changes: 34 additions & 0 deletions packages/core/lib/use-puck-history.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import type { AppState, History } from "../types";
import { PuckAction } from "../reducer";
import { useHotkeys } from "react-hotkeys-hook";
import { HistoryStore } from "./use-history-store";
import { getFrame } from "./get-frame";

export type PuckHistory = {
back: VoidFunction;
Expand All @@ -15,10 +16,12 @@ export function usePuckHistory({
dispatch,
initialAppState,
historyStore,
iframeEnabled,
}: {
dispatch: (action: PuckAction) => void;
initialAppState: AppState;
historyStore: HistoryStore;
iframeEnabled: boolean;
}) {
const back = () => {
if (historyStore.hasPast) {
Expand All @@ -39,6 +42,18 @@ export function usePuckHistory({
}
};

const backIframe = () => {
if (iframeEnabled) {
back();
}
};

const forwardIframe = () => {
if (iframeEnabled) {
forward();
}
};

const setHistories = (histories: History[]) => {
// dispatch the last history index or initial state
dispatch({
Expand All @@ -60,10 +75,29 @@ export function usePuckHistory({
}
};

const frame = getFrame();
const resolvedFrame =
typeof window !== "undefined" && frame !== document ? frame : undefined;

// Host hotkeys
useHotkeys("meta+z", back, { preventDefault: true });
useHotkeys("meta+shift+z", forward, { preventDefault: true });
useHotkeys("meta+y", forward, { preventDefault: true });

// Iframe hotkeys
useHotkeys("meta+z", backIframe, {
preventDefault: true,
document: resolvedFrame,
});
useHotkeys("meta+shift+z", forwardIframe, {
preventDefault: true,
document: resolvedFrame,
});
useHotkeys("meta+y", forwardIframe, {
preventDefault: true,
document: resolvedFrame,
});

return {
back,
forward,
Expand Down
2 changes: 1 addition & 1 deletion packages/core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@
"@measured/dnd": "16.6.0-canary.4cba1d1",
"deep-diff": "^1.0.2",
"object-hash": "^3.0.0",
"react-hotkeys-hook": "^4.4.1",
"react-hotkeys-hook": "^4.6.1",
"ua-parser-js": "^1.0.37",
"use-debounce": "^9.0.4",
"uuid": "^9.0.1"
Expand Down
2 changes: 1 addition & 1 deletion yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -12970,7 +12970,7 @@ react-from-json@^0.8.0:
resolved "https://registry.yarnpkg.com/react-from-json/-/react-from-json-0.8.0.tgz#c8e6c28a98180308be1eece3d22589a8c663d0dc"
integrity sha512-aVCZ7bQ5sUg4LhgW2qfY/Hfacqma1s600F7Z9GZqRqPtHu1JFi9gufS0o2YOIfo0e34OCqovoFZMl3VABMikCw==

react-hotkeys-hook@^4.4.1:
react-hotkeys-hook@^4.6.1:
version "4.6.1"
resolved "https://registry.yarnpkg.com/react-hotkeys-hook/-/react-hotkeys-hook-4.6.1.tgz#db9066c07377a1c8be067a238ab16e328266345a"
integrity sha512-XlZpbKUj9tkfgPgT9gA+1p7Ey6vFIZHttUjPqpTdyT5nqQ8mHL7elxvSbaC+dpSiHUSmr21Ya1mDxBZG3aje4Q==
Expand Down

0 comments on commit 1134e8b

Please sign in to comment.