ContentToc
Usage
Use the links prop with the page?.body?.toc?.links you get when fetching a page.
<script setup lang="ts">
import { createError, useAsyncData, useRoute } from '#app';
import { queryCollection } from '#imports';
const route = useRoute();
const { data: page } = await useAsyncData(route.path, () => queryCollection('docs').path(route.path).first());
if (!page.value) {
throw createError({ statusCode: 404, statusMessage: 'Page not found', fatal: true });
}
</script>
<template>
<PContentToc :links="page?.body?.toc?.links" />
</template>
Title
Use the title prop to change the title of the Table of Contents.
<script setup lang="ts">
const links = ref([
{
id: 'usage',
depth: 2,
text: 'Usage',
children: [
{
id: 'title',
depth: 3,
text: 'Title'
},
{
id: 'color',
depth: 3,
text: 'Color'
},
{
id: 'highlight',
depth: 3,
text: 'Highlight'
}
]
},
{
id: 'api',
depth: 2,
text: 'API',
children: [
{
id: 'props',
depth: 3,
text: 'Props'
},
{
id: 'slots',
depth: 3,
text: 'Slots'
}
]
},
{
id: 'theme',
depth: 2,
text: 'Theme'
}
])
</script>
<template>
<PContentToc title="On this page" :links="links" />
</template>
Color
Use the color prop to change the color of the links.
<script setup lang="ts">
const links = ref([
{
id: 'usage',
depth: 2,
text: 'Usage',
children: [
{
id: 'title',
depth: 3,
text: 'Title'
},
{
id: 'color',
depth: 3,
text: 'Color'
},
{
id: 'highlight',
depth: 3,
text: 'Highlight'
}
]
}
])
</script>
<template>
<PContentToc color="neutral" :links="links" />
</template>
Highlight
Use the highlight prop to display a highlighted border for the active item.
Use the highlight-color prop to change the color of the border. It defaults to the color prop.
<script setup lang="ts">
const links = ref([
{
id: 'usage',
depth: 2,
text: 'Usage',
children: [
{
id: 'title',
depth: 3,
text: 'Title'
},
{
id: 'color',
depth: 3,
text: 'Color'
},
{
id: 'highlight',
depth: 3,
text: 'Highlight'
}
]
}
])
</script>
<template>
<PContentToc highlight highlight-color="neutral" color="neutral" :links="links" />
</template>
Examples
Within a page
Use the ContentToc component in a page to display the Table of Contents:
<script setup lang="ts">
const route = useRoute();
const { data: page } = await useAsyncData(route.path, () => queryCollection('docs').path(route.path).first());
if (!page.value) {
throw createError({ statusCode: 404, statusMessage: 'Page not found', fatal: true });
}
</script>
<template>
<ExamplePage v-if="page">
<ExamplePageHeader :title="page.title" />
<ExamplePageBody>
<ContentRenderer
v-if="page.body"
:value="page"
/>
<PSeparator v-if="surround?.filter(Boolean).length" />
<PContentSurround :surround="(surround as any)" />
</ExamplePageBody>
<template
v-if="page?.body?.toc?.links?.length"
#right
>
<PContentToc :links="page.body.toc.links" />
</template>
</ExamplePage>
</template>
API
Props
| Prop | Default | Type |
|---|---|---|
as | 'nav' | anyThe element or component this component should render as. |
trailingIcon | appConfig.pohon.icons.chevronDown | string | objectThe icon displayed to collapse the content. |
title | t('contentToc.title') | stringThe title of the table of contents. |
color | 'primary' | "primary" | "secondary" | "success" | "info" | "warning" | "error" | "neutral" |
highlight | false | boolean Display a line next to the active link. |
highlightColor | 'primary' | "primary" | "secondary" | "success" | "info" | "warning" | "error" | "neutral" |
links | T[] | |
defaultOpen | boolean The open state of the collapsible when it is initially rendered. | |
open | boolean The controlled open state of the collapsible. Can be binded with | |
pohon | { root?: ClassValue; container?: ClassValue; top?: ClassValue; bottom?: ClassValue; trigger?: ClassValue; title?: ClassValue; trailing?: ClassValue; trailingIcon?: ClassValue; content?: ClassValue; list?: ClassValue; listWithChildren?: ClassValue; item?: ClassValue; itemWithChildren?: ClassValue; link?: ClassValue; linkText?: ClassValue; indicator?: ClassValue; } |
Slots
| Slot | Type |
|---|---|
leading | { open: boolean; pohon: object; } |
default | { open: boolean; } |
trailing | { open: boolean; pohon: object; } |
content | { links: T[]; } |
link | { link: T; } |
top | { links?: T[] | undefined; } |
bottom | { links?: T[] | undefined; } |
Emits
| Event | Type |
|---|---|
update:open | [value: boolean] |
move | [id: string] |
Theme
Below is the theme configuration skeleton for the PContentToc. Since the component is provided unstyled by default, you will need to fill in these values to apply your own custom look and feel. If you prefer to use our pre-built, opinionated styling, you can instead use our UnoCSS preset, this docs is using it as well.
export default defineAppConfig({
pohon: {
contentToc: {
slots: {
root: '',
container: '',
top: '',
bottom: '',
trigger: '',
title: '',
trailing: '',
trailingIcon: '',
content: '',
list: '',
listWithChildren: '',
item: '',
itemWithChildren: '',
link: '',
linkText: '',
indicator: ''
},
variants: {
color: {
primary: '',
secondary: '',
success: '',
info: '',
warning: '',
error: '',
neutral: ''
},
highlightColor: {
primary: {
indicator: ''
},
secondary: {
indicator: ''
},
success: {
indicator: ''
},
info: {
indicator: ''
},
warning: {
indicator: ''
},
error: {
indicator: ''
},
neutral: {
indicator: ''
}
},
active: {
false: {
link: ''
}
},
highlight: {
true: {
list: '',
item: ''
}
},
body: {
true: {
bottom: ''
}
}
},
defaultVariants: {
color: 'primary',
highlightColor: 'primary'
}
}
}
};
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import pohon from 'pohon-ui/vite'
export default defineAppConfig({
pohon: {
contentToc: {
slots: {
root: '',
container: '',
top: '',
bottom: '',
trigger: '',
title: '',
trailing: '',
trailingIcon: '',
content: '',
list: '',
listWithChildren: '',
item: '',
itemWithChildren: '',
link: '',
linkText: '',
indicator: ''
},
variants: {
color: {
primary: '',
secondary: '',
success: '',
info: '',
warning: '',
error: '',
neutral: ''
},
highlightColor: {
primary: {
indicator: ''
},
secondary: {
indicator: ''
},
success: {
indicator: ''
},
info: {
indicator: ''
},
warning: {
indicator: ''
},
error: {
indicator: ''
},
neutral: {
indicator: ''
}
},
active: {
false: {
link: ''
}
},
highlight: {
true: {
list: '',
item: ''
}
},
body: {
true: {
bottom: ''
}
}
},
defaultVariants: {
color: 'primary',
highlightColor: 'primary'
}
}
}
};