Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions examples/01-basic/14-shadowdom/.bnexample.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
{
"playground": true,
"docs": false,
"author": "matthewlipski",
"tags": ["Basic"]
}
7 changes: 7 additions & 0 deletions examples/01-basic/14-shadowdom/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
# Shadow DOM

This example shows how to render the BlockNote editor inside a Shadow DOM.

**Relevant Docs:**

- [Editor Setup](/docs/getting-started/editor-setup)
14 changes: 14 additions & 0 deletions examples/01-basic/14-shadowdom/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Shadow DOM</title>
<script>
<!-- AUTO-GENERATED FILE, DO NOT EDIT DIRECTLY -->
</script>
</head>
<body>
<div id="root"></div>
<script type="module" src="./main.tsx"></script>
</body>
</html>
11 changes: 11 additions & 0 deletions examples/01-basic/14-shadowdom/main.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// AUTO-GENERATED FILE, DO NOT EDIT DIRECTLY
import React from "react";
import { createRoot } from "react-dom/client";
import App from "./src/App.jsx";

const root = createRoot(document.getElementById("root")!);
root.render(
<React.StrictMode>
<App />
</React.StrictMode>
);
31 changes: 31 additions & 0 deletions examples/01-basic/14-shadowdom/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
{
"name": "@blocknote/example-basic-shadowdom",
"description": "AUTO-GENERATED FILE, DO NOT EDIT DIRECTLY",
"type": "module",
"private": true,
"version": "0.12.4",
"scripts": {
"start": "vite",
"dev": "vite",
"build:prod": "tsc && vite build",
"preview": "vite preview"
},
"dependencies": {
"@blocknote/ariakit": "latest",
"@blocknote/core": "latest",
"@blocknote/mantine": "latest",
"@blocknote/react": "latest",
"@blocknote/shadcn": "latest",
"@mantine/core": "^8.3.4",
"@mantine/hooks": "^8.3.4",
"@mantine/utils": "^6.0.22",
"react": "^19.2.0",
"react-dom": "^19.2.0"
},
"devDependencies": {
"@types/react": "^19.2.2",
"@types/react-dom": "^19.2.1",
"@vitejs/plugin-react": "^4.7.0",
"vite": "^5.4.20"
}
}
46 changes: 46 additions & 0 deletions examples/01-basic/14-shadowdom/src/App.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
import { BlockNoteView } from "@blocknote/mantine";
import { useCreateBlockNote } from "@blocknote/react";

import { useEffect, useRef, useState } from "react";
import { createPortal } from "react-dom";

import interCss from "@blocknote/core/fonts/inter.css?inline";
import mantineCss from "@blocknote/mantine/style.css?inline";

function ShadowWrapper(props: { children: React.ReactNode }) {
const host = useRef<HTMLDivElement>(null);
const [shadowRoot, setShadowRoot] = useState<ShadowRoot | null>(null);

useEffect(() => {
if (host.current && !shadowRoot) {
const root = host.current.shadowRoot || host.current.attachShadow({ mode: "open" });
setShadowRoot(root);
}
}, [shadowRoot]);

return (
<div ref={host}>
{shadowRoot &&
createPortal(
<>
<style>{interCss}</style>
<style>{mantineCss}</style>
{props.children}
</>,
shadowRoot as any
)}
</div>
);
}

export default function App() {
// Creates a new editor instance.
const editor = useCreateBlockNote();

// Renders the editor instance using a React component.
return (
<ShadowWrapper>
<BlockNoteView editor={editor} />
</ShadowWrapper>
);
}
6 changes: 6 additions & 0 deletions examples/01-basic/14-shadowdom/src/vite-env.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
/// <reference types="vite/client" />

declare module "*?inline" {
const content: string;
export default content;
}
36 changes: 36 additions & 0 deletions examples/01-basic/14-shadowdom/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
{
"__comment": "AUTO-GENERATED FILE, DO NOT EDIT DIRECTLY",
"compilerOptions": {
"target": "ESNext",
"useDefineForClassFields": true,
"lib": [
"DOM",
"DOM.Iterable",
"ESNext"
],
"allowJs": false,
"skipLibCheck": true,
"esModuleInterop": false,
"allowSyntheticDefaultImports": true,
"strict": true,
"forceConsistentCasingInFileNames": true,
"module": "ESNext",
"moduleResolution": "bundler",
"resolveJsonModule": true,
"isolatedModules": true,
"noEmit": true,
"jsx": "react-jsx",
"composite": true
},
"include": [
"."
],
"__ADD_FOR_LOCAL_DEV_references": [
{
"path": "../../../packages/core/"
},
{
"path": "../../../packages/react/"
}
]
}
32 changes: 32 additions & 0 deletions examples/01-basic/14-shadowdom/vite.config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
// AUTO-GENERATED FILE, DO NOT EDIT DIRECTLY
import react from "@vitejs/plugin-react";
import * as fs from "fs";
import * as path from "path";
import { defineConfig } from "vite";
// import eslintPlugin from "vite-plugin-eslint";
// https://vitejs.dev/config/
export default defineConfig((conf) => ({
plugins: [react()],
optimizeDeps: {},
build: {
sourcemap: true,
},
resolve: {
alias:
conf.command === "build" ||
!fs.existsSync(path.resolve(__dirname, "../../packages/core/src"))
? {}
: ({
// Comment out the lines below to load a built version of blocknote
// or, keep as is to load live from sources with live reload working
"@blocknote/core": path.resolve(
__dirname,
"../../packages/core/src/"
),
"@blocknote/react": path.resolve(
__dirname,
"../../packages/react/src/"
),
} as any),
},
}));
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ function MUISuggestionMenuItem(

const overflow = elementOverflow(
itemRef.current,
document.querySelector(
itemRef.current.closest(
`.MuiPaper-root:has([aria-label="suggestion-menu"])`,
)!,
);
Expand Down
2 changes: 1 addition & 1 deletion packages/ariakit/src/suggestionMenu/SuggestionMenuItem.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ export const SuggestionMenuItem = forwardRef<

const overflow = elementOverflow(
itemRef.current,
document.querySelector(".bn-suggestion-menu, #ai-suggestion-menu")!, // TODO
itemRef.current.closest(".bn-suggestion-menu, #ai-suggestion-menu")!,
);

if (overflow === "top") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ export const GridSuggestionMenuItem = forwardRef<

const overflow = elementOverflow(
itemRef.current,
document.querySelector(".bn-grid-suggestion-menu")!,
itemRef.current.closest(".bn-grid-suggestion-menu")!,
);

if (overflow === "top") {
Expand Down
7 changes: 3 additions & 4 deletions packages/mantine/src/suggestionMenu/SuggestionMenuItem.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,10 +25,9 @@ export const SuggestionMenuItem = forwardRef<
return;
}

const overflow = elementOverflow(
itemRef.current,
document.querySelector(".bn-suggestion-menu, #ai-suggestion-menu")!, // TODO
);
const overflow = elementOverflow(itemRef.current, itemRef.current.closest(
".bn-suggestion-menu, #ai-suggestion-menu"
)!);

if (overflow === "top") {
itemRef.current.scrollIntoView(true);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ export const GridSuggestionMenuItem = forwardRef<

const overflow = elementOverflow(
itemRef.current,
document.querySelector(".bn-grid-suggestion-menu")!,
itemRef.current.closest(".bn-grid-suggestion-menu")!,
);

if (overflow === "top") {
Expand Down
2 changes: 1 addition & 1 deletion packages/shadcn/src/suggestionMenu/SuggestionMenuItem.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ export const SuggestionMenuItem = forwardRef<

const overflow = elementOverflow(
itemRef.current,
document.querySelector(".bn-suggestion-menu, #ai-suggestion-menu")!, // TODO
itemRef.current.closest(".bn-suggestion-menu, #ai-suggestion-menu")!,
);
if (overflow === "top") {
itemRef.current.scrollIntoView(true);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ export const GridSuggestionMenuItem = forwardRef<

const overflow = elementOverflow(
itemRef.current,
document.querySelector(".bn-grid-suggestion-menu")!,
itemRef.current.closest(".bn-grid-suggestion-menu")!,
);

if (overflow === "top") {
Expand Down
Loading
Loading