Un panel de navegación de tabla de contenidos que muestra y resalta los encabezados de la página actual.
El componente OnThisPage renderiza un panel de navegación flotante que lista los encabezados del documento actual, resaltando dinámicamente las secciones activas mientras el usuario hace scroll.
La primitiva OnThisPage es neutra de estilo: aporta estructura, el seguimiento de scroll con IntersectionObserver, la matemática del indicador de pista activa y atributos de estado data-*. Todo lo visual pertenece a tu tema — colores, bordes, sangrías, el resaltado activo. Estiliza los estados con variantes de Tailwind v4 (data-active:text-primary-500) o CSS puro ([data-active] { ... }).
Usando los módulos de la primitiva OnThisPage, puedes ensamblar una tabla de contenidos totalmente personalizada. El siguiente ejemplo muestra cómo componer un layout con títulos personalizados, contenedores de lista, líneas indicadoras de actividad y comportamientos de scroll suaves:
tsx
// docs/components/CustomTOC.tsximport { useRef } from 'react'import { OnThisPage, AnchorProvider, ScrollProvider,} from 'boltdocs/primitives'import { useRoutes } from 'boltdocs/client'export default function CustomTOC() { const { currentRoute } = useRoutes() const scrollContainerRef = useRef<HTMLDivElement>(null) const headings = currentRoute?.headings || [] if (headings.length === 0) return null // Convierte la base de datos de encabezados a una estructura TOC estándar const tocItems = headings.map((h) => ({ title: h.text, url: `#${h.id}`, depth: h.level, })) return ( <OnThisPage className="hidden xl:block w-toc py-4 pl-6 pr-4"> {/* 1. Encabezado de título estático */} <OnThisPage.Header className="text-xs font-bold uppercase tracking-wider text-muted mb-4"> Tabla de Contenidos </OnThisPage.Header> {/* 2. Proveedores de contexto de seguimiento de scroll */} <AnchorProvider toc={tocItems} single={false}> <ScrollProvider containerRef={scrollContainerRef}> {/* 3. Viewport con scroll */} <OnThisPage.Content ref={scrollContainerRef} className="max-h-[80vh] pb-12" fadeClassName="bg-linear-to-b from-transparent to-main" > {/* 4. Lista + indicador de pista activa */} <OnThisPage.List className="relative border-l border-subtle space-y-0.5 text-sm"> <OnThisPage.Indicator className="-left-px w-0.5 rounded-full bg-primary-500" /> {headings.map((h) => ( <OnThisPage.Item key={h.id} level={h.level} className="data-[level=3]:pl-3" > <OnThisPage.Link href={`#${h.id}`} className="block py-0.5 pl-4 text-[13px] transition-colors text-muted hover:text-body data-active:text-primary-500" > {h.text} </OnThisPage.Link> </OnThisPage.Item> ))} </OnThisPage.List> </OnThisPage.Content> </ScrollProvider> </AnchorProvider> </OnThisPage> )}
[!TIP]
Si no quieres mapear los elementos manualmente, puedes usar el envoltorio de alto nivel <OnThisPage.Tree headings={headings} /> para montar automáticamente los observadores, indicadores y enlaces dentro de un layout activo. Tree acepta los slots className (lista), itemClassName, linkClassName, indicatorClassName, contentClassName y fadeClassName.
Las primitivas de OnThisPage exponen su estado a través de atributos data-*, presentes solo cuando son verdaderos. Decide tus propios colores y tratamientos desde CSS.
Atributo
Se Emite En
Presente Cuando
data-active
enlace OnThisPage.Link
El encabezado es la sección activa actual
data-level
OnThisPage.Item
Profundidad de jerarquía del encabezado (p. ej. 2, 3) — usa data-[level=3]:pl-3 para sangría
Si estás construyendo un rastreador totalmente personalizado, puedes importar y envolver tu layout en los proveedores de contexto React expuestos a través de OnThisPage:
Proveedor de Contexto
Descripción
Props
AnchorProvider
Observa eventos de scroll con IntersectionObserver y rastrea el encabezado activo.