Skip to content

Commit

Permalink
feat(theme): add ability to inject data attributes from query-string …
Browse files Browse the repository at this point in the history
…- possibility to create an iframe/embed variant of a page (#9028)
  • Loading branch information
slorber committed May 31, 2023
1 parent 444c157 commit 2d35edf
Show file tree
Hide file tree
Showing 3 changed files with 57 additions and 8 deletions.
27 changes: 21 additions & 6 deletions packages/docusaurus-theme-classic/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,10 @@ const ContextReplacementPlugin = requireFromDocusaurusCore(
// Need to be inlined to prevent dark mode FOUC
// Make sure the key is the same as the one in `/theme/hooks/useTheme.js`
const ThemeStorageKey = 'theme';
// Support for ?docusaurus-theme=dark
const ThemeQueryStringKey = 'docusaurus-theme';
// Support for ?docusaurus-data-mode=embed&docusaurus-data-myAttr=42
const DataQueryStringPrefixKey = 'docusaurus-data-';

const noFlashColorMode = ({
defaultMode,
Expand All @@ -42,19 +45,15 @@ const noFlashColorMode = ({
}
function getQueryStringTheme() {
var theme = null;
try {
theme = new URLSearchParams(window.location.search).get('${ThemeQueryStringKey}')
return new URLSearchParams(window.location.search).get('${ThemeQueryStringKey}')
} catch(e) {}
return theme;
}
function getStoredTheme() {
var theme = null;
try {
theme = localStorage.getItem('${ThemeStorageKey}');
return localStorage.getItem('${ThemeStorageKey}');
} catch (err) {}
return theme;
}
var initialTheme = getQueryStringTheme() || getStoredTheme();
Expand All @@ -77,6 +76,21 @@ const noFlashColorMode = ({
}
})();`;

/* language=js */
const DataAttributeQueryStringInlineJavaScript = `
(function() {
try {
const entries = new URLSearchParams(window.location.search).entries();
for (var [searchKey, value] of entries) {
if (searchKey.startsWith('${DataQueryStringPrefixKey}')) {
var key = searchKey.replace('${DataQueryStringPrefixKey}',"data-")
document.documentElement.setAttribute(key, value);
}
}
} catch(e) {}
})();
`;

// Duplicated constant. Unfortunately we can't import it from theme-common, as
// we need to support older nodejs versions without ESM support
// TODO: import from theme-common once we only support Node.js with ESM support
Expand Down Expand Up @@ -205,6 +219,7 @@ export default function themeClassic(
tagName: 'script',
innerHTML: `
${noFlashColorMode(colorMode)}
${DataAttributeQueryStringInlineJavaScript}
${announcementBar ? AnnouncementBarInlineJavaScript : ''}
`,
},
Expand Down
30 changes: 28 additions & 2 deletions website/docs/styling-layout.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ description: A Docusaurus site is a pre-rendered single-page React application.
---

import ColorGenerator from '@site/src/components/ColorGenerator';
import IframeWindow from '@site/src/components/BrowserWindow/IframeWindow';

# Styling and Layout

Expand Down Expand Up @@ -133,8 +134,33 @@ It is possible to initialize the Docusaurus theme directly from a `docusaurus-th

Examples:

- [`https://docusaurus.io/?docusaurus-theme=dark`](https://docusaurus.io/?docusaurus-theme=dark)
- [`https://docusaurus.io/docs/configuration?docusaurus-theme=light`](https://docusaurus.io/docs/configuration?docusaurus-theme=light)
<IframeWindow url="/docs/?docusaurus-theme=dark" />

<IframeWindow url="/docs/configuration?docusaurus-theme=light" />

:::

### Data Attributes {#data-attributes}

It is possible to inject `<html>` data attributes with query string parameters following the `docusaurus-data-<key>` pattern. This gives you the flexibility to style a page differently based on the query string.

For example, let's render one of our pages with a red border and no navbar:

```css title="/src/css/custom.css"
html[data-navbar='false'] .navbar {
display: none;
}

html[data-red-border] div#__docusaurus {
border: red solid thick;
}
```

<IframeWindow url="/docs/?docusaurus-data-navbar=false&docusaurus-data-red-border" />

:::tip Iframe Mode

If you plan to embed some Docusaurus pages on another site though an iframe, it can be useful to create an alternative display mode and use iframe urls such as `https://mysite.com/docs/myDoc?docusaurus-data-mode=iframe`. It is your responsibility to provide the additional styles and decide which UI elements you want to keep or hide.

:::

Expand Down
8 changes: 8 additions & 0 deletions website/src/css/custom.css
Original file line number Diff line number Diff line change
Expand Up @@ -230,3 +230,11 @@ div[class^='announcementBar_'] {
[data-theme='dark'] [data-rmiz-modal-overlay='visible'] {
background-color: rgba(0 0 0 / 95%);
}

html[data-navbar='false'] .navbar {
display: none;
}

html[data-red-border] div#__docusaurus {
border: red solid thick;
}

0 comments on commit 2d35edf

Please sign in to comment.