diff --git a/packages/core/components/AutoFrame/index.tsx b/packages/core/components/AutoFrame/index.tsx index a0d8580f4c..5e15619ee2 100644 --- a/packages/core/components/AutoFrame/index.tsx +++ b/packages/core/components/AutoFrame/index.tsx @@ -6,11 +6,24 @@ import { useEffect, useState, } from "react"; -import hash from "object-hash"; import { createPortal } from "react-dom"; const styleSelector = 'style, link[rel="stylesheet"]'; +/** + * Fast, non-cryptographic djb2 hash over a string. + * Replaces `object-hash` which serialises the full outerHTML via JSON + * and is O(n) on the CSS string length — catastrophically slow when + * many large style nodes are present. + */ +const fastHash = (str: string): string => { + let h = 5381; + for (let i = 0; i < str.length; i++) { + h = (((h << 5) + h) ^ str.charCodeAt(i)) >>> 0; + } + return h.toString(36); +}; + const collectStyles = (doc: Document) => { const collected: HTMLElement[] = []; @@ -66,6 +79,25 @@ const syncAttributes = (sourceElement: Element, targetElement: Element) => { const defer = (fn: () => void) => setTimeout(fn, 0); +/** + * Compute a cheap hash key for a style element. + * - For elements we key on the href (a short string). + * - For