Important
A remark plugin to add obsidian style callouts to markdown.
> [!note] title here
> body here
# npm
npm install @r4ai/remark-callout
# pnpm
pnpm install @r4ai/remark-callout
# bun
bun add @r4ai/remark-callout
See Usage.
import remarkParse from "remark-parse";
import { unified } from "unified";
import remarkCallout from "@r4ai/remark-callout";
import remarkRehype from "remark-rehype";
import rehypeRaw from "rehype-raw";
import rehypeStringify from "rehype-stringify";
const md = `
> [!note] title here
> body here
`;
const html = unified()
.use(remarkParse)
.use(remarkCallout)
.use(remarkRehype, { allowDangerousHtml: true })
.use(rehypeRaw)
.use(rehypeStringify)
.processSync(md)
.toString();
console.log(html);
yields:
<div data-callout data-callout-type="note">
<div data-callout-title>title here</div>
<div data-callout-body>
<p>body here</p>
</div>
</div>
Warning
To display the callout icon as HTML using options.icon
or options.foldIcon
, you need to set the allowDangerousHtml
option to true
in remark-rehype
and add rehype-raw
as a plugin.
-
Install the plugin:
npm install @r4ai/remark-callout
-
Add
@r4ai/remark-callout
to remark plugins in your astro config file (e.g.astro.config.ts
):// astro.config.ts import remarkCallout from "@r4ai/remark-callout"; export default defineConfig({ // ... markdown: { // ... remarkPlugins: [ // ... remarkCallout, ], }, });
Note: This plugin works fine in MDX files as well. For instructions on how to use MDX with Astro, see @astrojs/mdx.
-
Start using callouts in your markdown or mdx files:
> [!note] title here > body here
yields:
<div data-callout data-callout-type="note"> <div data-callout-title>title here</div> <div data-callout-body> <p>body here</p> </div> </div>
Now you can style the callouts using CSS. Following is an example of how you can style the callouts using Tailwind CSS:
remark-callout/packages/website/src/pages/playground/_callout.css
Lines 1 to 384 in 40d857e
[data-callout] { & { @apply my-6 space-y-2 rounded-lg border border-blue-600/20 bg-blue-400/20 p-4 pb-5 dark:border-blue-800/20 dark:bg-blue-600/10; } & > [data-callout-title] { & { @apply flex flex-row items-start gap-2 p-0 font-bold text-blue-500; } &:not:only-child { @apply mb-2; } &:empty::after { content: "Note"; } &::before { @apply mt-1 block h-5 w-5 bg-current content-[""]; mask-repeat: no-repeat; mask-size: cover; /* lucide-pencil */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0iTTE3IDNhMi44NSAyLjgzIDAgMSAxIDQgNEw3LjUgMjAuNUwyIDIybDEuNS01LjVabS0yIDJsNCA0Ii8+PC9zdmc+"); } } & > [data-callout-body] { & { @apply space-y-2; } & > * { @apply m-0; } } } details[data-callout] > summary[data-callout-title] { & { @apply cursor-pointer; } &::after { @apply w-full bg-right bg-no-repeat; content: ""; /* lucide:chevron-right */ background-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iIzg4ODg4OCIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBzdHJva2Utd2lkdGg9IjIiIGQ9Im05IDE4bDYtNmwtNi02Ii8+PC9zdmc+"); background-size: 1.5rem; } &:not(:empty)::after { @apply my-auto ml-auto h-6 w-6; } } details[data-callout][open] > summary[data-callout-title]::after { /* lucide:chevron-down */ background-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iIzg4ODg4OCIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBzdHJva2Utd2lkdGg9IjIiIGQ9Im02IDlsNiA2bDYtNiIvPjwvc3ZnPg=="); } [data-callout][data-callout-type="info"] { & { @apply border-blue-600/20 bg-blue-400/20 dark:border-blue-800/20 dark:bg-blue-600/10; } & > [data-callout-title] { & { @apply text-blue-500; } &:empty::after { content: "Info"; } &::before { /* lucide:info */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxnIGZpbGw9Im5vbmUiIHN0cm9rZT0iIzg4ODg4OCIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBzdHJva2Utd2lkdGg9IjIiPjxjaXJjbGUgY3g9IjEyIiBjeT0iMTIiIHI9IjEwIi8+PHBhdGggZD0iTTEyIDE2di00bTAtNGguMDEiLz48L2c+PC9zdmc+"); } } } [data-callout][data-callout-type="todo"] { & { @apply border-blue-600/20 bg-blue-400/20 dark:border-blue-800/20 dark:bg-blue-600/10; } & > [data-callout-title] { & { @apply text-blue-500; } &:empty::after { content: "ToDo"; } &::before { /* lucide:circle-check-big */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxnIGZpbGw9Im5vbmUiIHN0cm9rZT0iIzg4ODg4OCIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBzdHJva2Utd2lkdGg9IjIiPjxwYXRoIGQ9Ik0yMiAxMS4wOFYxMmExMCAxMCAwIDEgMS01LjkzLTkuMTQiLz48cGF0aCBkPSJtOSAxMWwzIDNMMjIgNCIvPjwvZz48L3N2Zz4="); } } } [data-callout][data-callout-type="abstract"], [data-callout][data-callout-type="summary"], [data-callout][data-callout-type="tldr"] { & { @apply border-cyan-600/20 bg-cyan-400/20 dark:border-cyan-800/20 dark:bg-cyan-600/10; } & > [data-callout-title] { & { @apply text-cyan-500; } &::before { /* lucide:clipboard-list */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxnIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiI+PHJlY3Qgd2lkdGg9IjgiIGhlaWdodD0iNCIgeD0iOCIgeT0iMiIgcng9IjEiIHJ5PSIxIi8+PHBhdGggZD0iTTE2IDRoMmEyIDIgMCAwIDEgMiAydjE0YTIgMiAwIDAgMS0yIDJINmEyIDIgMCAwIDEtMi0yVjZhMiAyIDAgMCAxIDItMmgybTQgN2g0bS00IDVoNG0tOC01aC4wMU04IDE2aC4wMSIvPjwvZz48L3N2Zz4="); } } } [data-callout][data-callout-type="abstract"] > [data-callout-title]:empty::after { content: "Abstract"; } [data-callout][data-callout-type="summary"] > [data-callout-title]:empty::after { content: "Summary"; } [data-callout][data-callout-type="tldr"] > [data-callout-title]:empty::after { content: "TL;DR"; } [data-callout][data-callout-type="tip"], [data-callout][data-callout-type="hint"], [data-callout][data-callout-type="important"] { & { @apply border-cyan-600/20 bg-cyan-400/20 dark:border-cyan-800/20 dark:bg-cyan-600/10; } & > [data-callout-title] { & { @apply text-cyan-500; } &::before { /* lucide:flame */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0iTTguNSAxNC41QTIuNSAyLjUgMCAwIDAgMTEgMTJjMC0xLjM4LS41LTItMS0zYy0xLjA3Mi0yLjE0My0uMjI0LTQuMDU0IDItNmMuNSAyLjUgMiA0LjkgNCA2LjVjMiAxLjYgMyAzLjUgMyA1LjVhNyA3IDAgMSAxLTE0IDBjMC0xLjE1My40MzMtMi4yOTQgMS0zYTIuNSAyLjUgMCAwIDAgMi41IDIuNSIvPjwvc3ZnPg=="); } } } [data-callout][data-callout-type="tip"] > [data-callout-title]:empty::after { content: "Tip"; } [data-callout][data-callout-type="hint"] > [data-callout-title]:empty::after { content: "Hint"; } [data-callout][data-callout-type="important"] > [data-callout-title]:empty::after { content: "Important"; } [data-callout][data-callout-type="success"], [data-callout][data-callout-type="check"], [data-callout][data-callout-type="done"] { & { @apply border-green-600/20 bg-green-400/20 dark:border-green-800/20 dark:bg-green-600/10; } & > [data-callout-title] { & { @apply text-green-500; } &::before { /* lucide:check */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0iTTIwIDZMOSAxN2wtNS01Ii8+PC9zdmc+"); } } } [data-callout][data-callout-type="success"] > [data-callout-title]:empty::after { content: "Success"; } [data-callout][data-callout-type="check"] > [data-callout-title]:empty::after { content: "Check"; } [data-callout][data-callout-type="done"] > [data-callout-title]:empty::after { content: "Done"; } [data-callout][data-callout-type="question"], [data-callout][data-callout-type="help"], [data-callout][data-callout-type="faq"] { & { @apply border-orange-600/20 bg-orange-400/20 dark:border-orange-800/20 dark:bg-orange-600/10; } & > [data-callout-title] { & { @apply text-orange-500; } &::before { /* lucide:circle-help */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxnIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiI+PGNpcmNsZSBjeD0iMTIiIGN5PSIxMiIgcj0iMTAiLz48cGF0aCBkPSJNOS4wOSA5YTMgMyAwIDAgMSA1LjgzIDFjMCAyLTMgMy0zIDNtLjA4IDRoLjAxIi8+PC9nPjwvc3ZnPg=="); } } } [data-callout][data-callout-type="question"] > [data-callout-title]:empty::after { content: "Question"; } [data-callout][data-callout-type="help"] > [data-callout-title]:empty::after { content: "Help"; } [data-callout][data-callout-type="faq"] > [data-callout-title]:empty::after { content: "FAQ"; } [data-callout][data-callout-type="warning"], [data-callout][data-callout-type="caution"], [data-callout][data-callout-type="attention"] { & { @apply border-orange-600/20 bg-orange-400/20 dark:border-orange-800/20 dark:bg-orange-600/10; } & > [data-callout-title] { & { @apply text-orange-500; } &::before { /* lucide:triangle-alert */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0ibTIxLjczIDE4bC04LTE0YTIgMiAwIDAgMC0zLjQ4IDBsLTggMTRBMiAyIDAgMCAwIDQgMjFoMTZhMiAyIDAgMCAwIDEuNzMtM00xMiA5djRtMCA0aC4wMSIvPjwvc3ZnPg=="); } } } [data-callout][data-callout-type="warning"] > [data-callout-title]:empty::after { content: "Warning"; } [data-callout][data-callout-type="caution"] > [data-callout-title]:empty::after { content: "Caution"; } [data-callout][data-callout-type="attention"] > [data-callout-title]:empty::after { content: "Attention"; } [data-callout][data-callout-type="failure"], [data-callout][data-callout-type="fail"], [data-callout][data-callout-type="missing"] { & { @apply border-red-600/20 bg-red-400/20 dark:border-red-800/20 dark:bg-red-600/10; } & > [data-callout-title] { & { @apply text-red-500; } &::before { /* lucide:check */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0iTTIwIDZMOSAxN2wtNS01Ii8+PC9zdmc+"); } } } [data-callout][data-callout-type="failure"] > [data-callout-title]:empty::after { content: "Failure"; } [data-callout][data-callout-type="fail"] > [data-callout-title]:empty::after { content: "Fail"; } [data-callout][data-callout-type="missing"] > [data-callout-title]:empty::after { content: "Missing"; } [data-callout][data-callout-type="danger"], [data-callout][data-callout-type="error"] { & { @apply border-red-600/20 bg-red-400/20 dark:border-red-800/20 dark:bg-red-600/10; } & > [data-callout-title] { & { @apply text-red-500; } &::before { /* lucide:zap */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9ImN1cnJlbnRDb2xvciIgc3Ryb2tlLXdpZHRoPSIyIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIGNsYXNzPSJsdWNpZGUgbHVjaWRlLXphcCI+PHBhdGggZD0iTTQgMTRhMSAxIDAgMCAxLS43OC0xLjYzbDkuOS0xMC4yYS41LjUgMCAwIDEgLjg2LjQ2bC0xLjkyIDYuMDJBMSAxIDAgMCAwIDEzIDEwaDdhMSAxIDAgMCAxIC43OCAxLjYzbC05LjkgMTAuMmEuNS41IDAgMCAxLS44Ni0uNDZsMS45Mi02LjAyQTEgMSAwIDAgMCAxMSAxNHoiLz48L3N2Zz4="); } } } [data-callout][data-callout-type="danger"] > [data-callout-title]:empty::after { content: "Danger"; } [data-callout][data-callout-type="error"] > [data-callout-title]:empty::after { content: "Error"; } [data-callout][data-callout-type="bug"] { & { @apply border-red-600/20 bg-red-400/20 dark:border-red-800/20 dark:bg-red-600/10; } & > [data-callout-title] { & { @apply text-red-500; } &::before { /* lucide:bug */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxnIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiI+PHBhdGggZD0ibTggMmwxLjg4IDEuODhtNC4yNCAwTDE2IDJNOSA3LjEzdi0xYTMuMDAzIDMuMDAzIDAgMSAxIDYgMHYxIi8+PHBhdGggZD0iTTEyIDIwYy0zLjMgMC02LTIuNy02LTZ2LTNhNCA0IDAgMCAxIDQtNGg0YTQgNCAwIDAgMSA0IDR2M2MwIDMuMy0yLjcgNi02IDZtMCAwdi05Ii8+PHBhdGggZD0iTTYuNTMgOUM0LjYgOC44IDMgNy4xIDMgNW0zIDhIMm0xIDhjMC0yLjEgMS43LTMuOSAzLjgtNE0yMC45NyA1YzAgMi4xLTEuNiAzLjgtMy41IDRNMjIgMTNoLTRtLS44IDRjMi4xLjEgMy44IDEuOSAzLjggNCIvPjwvZz48L3N2Zz4="); } } } [data-callout][data-callout-type="bug"] > [data-callout-title]:empty::after { content: "Bug"; } [data-callout][data-callout-type="example"] { & { @apply border-purple-600/20 bg-purple-400/20 dark:border-purple-800/20 dark:bg-purple-600/10; } & > [data-callout-title] { & { @apply text-purple-500; } &::before { /* lucide:list */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0iTTggNmgxM004IDEyaDEzTTggMThoMTNNMyA2aC4wMU0zIDEyaC4wMU0zIDE4aC4wMSIvPjwvc3ZnPg=="); } } } [data-callout][data-callout-type="example"] > [data-callout-title]:empty::after { content: "Example"; } [data-callout][data-callout-type="quote"], [data-callout][data-callout-type="cite"] { & { @apply border-zinc-600/20 bg-zinc-400/20 dark:border-zinc-800/20 dark:bg-zinc-600/15; } & > [data-callout-title] { & { @apply text-zinc-500; } &::before { /* lucide:quote */ mask-image: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxZW0iIGhlaWdodD0iMWVtIiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGZpbGw9Im5vbmUiIHN0cm9rZT0iY3VycmVudENvbG9yIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIHN0cm9rZS13aWR0aD0iMiIgZD0iTTMgMjFjMyAwIDctMSA3LThWNWMwLTEuMjUtLjc1Ni0yLjAxNy0yLTJINGMtMS4yNSAwLTIgLjc1LTIgMS45NzJWMTFjMCAxLjI1Ljc1IDIgMiAyYzEgMCAxIDAgMSAxdjFjMCAxLTEgMi0yIDJzLTEgLjAwOC0xIDEuMDMxVjIwYzAgMSAwIDEgMSAxbTEyIDBjMyAwIDctMSA3LThWNWMwLTEuMjUtLjc1Ny0yLjAxNy0yLTJoLTRjLTEuMjUgMC0yIC43NS0yIDEuOTcyVjExYzAgMS4yNS43NSAyIDIgMmguNzVjMCAyLjI1LjI1IDQtMi43NSA0djNjMCAxIDAgMSAxIDEiLz48L3N2Zz4="); } } } [data-callout][data-callout-type="quote"] > [data-callout-title]:empty::after { content: "Quote"; } [data-callout][data-callout-type="cite"] > [data-callout-title]:empty::after { content: "Cite"; } To use the above CSS, you need to configure Astro's TailwindCSS integration to support nested syntax:
// astro.config.ts import { defineConfig } from 'astro/config'; import tailwind from '@astrojs/tailwind'; export default defineConfig({ integrations: [ tailwind({ // Example: Allow writing nested CSS declarations // alongside Tailwind's syntax nesting: true, }), ], });
cf. https://docs.astro.build/en/guides/integrations-guide/tailwind/#nesting
Or if you are using MDX, you can use custom components to style the callouts:
// astro.config.ts import { remarkCallout } from "@r4ai/remark-callout"; export default defineConfig({ // ... markdown: { // ... remarkPlugins: [ // ... [ remarkCallout, { root: (callout) => ({ tagName: "callout", properties: { calloutType: callout.type, isFoldable: String(callout.isFoldable), }, }), title: (callout) => ({ tagName: "callout-title", properties: { calloutType: callout.type, isFoldable: String(callout.isFoldable), }, }), }, ], ], }, });
--- // src/components/Callout.astro type Props = { calloutType: string isFoldable: boolean } const { calloutType, isFoldable } = Astro.props --- <div class={/* Your TailwindCSS style here */} > <slot /> </div>
--- // src/components/CalloutTitle.astro type Props = { callouType: string isFoldable: boolean } const { calloutType, isFoldable } = Astro.props --- <div class={/* Your TailwindCSS style here */} > <SomeIconComponent /> <slot /> </div>
--- // src/pages/callout-example.astro import { Content, components } from "../content.mdx"; import Callout from "../components/Callout.astro"; import CalloutTitle from "../components/CalloutTitle.astro"; --- <Content components={{ ...components, callout: Callout, "callout-title": CalloutTitle }} />
See r4ai.github.io/remark-callout/docs/en/api-reference/type-aliases/options
Command | Description |
---|---|
bun install |
Install dependencies |
bun run build |
Build the packages |
bun run test |
Run tests |
bun run test:coverage |
Run tests with coverage |
bun run check |
Check the code |
bun run check:write |
Check and fix the code |
bun run changeset |
Create a changeset |
Directory | Description |
---|---|
examples/nextjs |
Example Next.js project |
packages/remark-callout |
The remark-callout package |
packages/website |
The documentation website for remark-callout |
-
Install dependencies:
bun install
-
Build the packages:
bun run build
-
Check and fix the code:
bun run check:write
-
Run tests with coverage:
bun run test:coverage
-
Launch the documentation website:
bun run --cwd packages/website dev