Demos
How to import
import { Anchor } from '@fibrous/semi-ui-solid';
Basic Usage
Use Link to create an anchor, click it to jump to the hash tag location.
Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<Anchor>
<Anchor.Link href="#基本示例" title="基本示例" />
<Anchor.Link href="#组件" title="组件" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
);
}Integrated Usage
You can use getContainer, targetOffset, offsetTop, and style to create a out of the box hyperAnchor.Link navigation bar.
-
getContainer:you can set the container of scroll content with
getContainerproperty. Its default value iswindow. -
targetOffset: you can set the distance between the anchor point and the top of the container by setting
targetOffset. -
style:Anchor does not position itself. Position it yourself with the
styleobject, for exampleposition: fixed. -
offsetTop:
offsetTopcan trigger the current Link switch when the scrolling content reaches a specified offset from the top of the container.
import { Anchor } from '@fibrous/semi-ui-solid';
function AnchorExample() {
const getContainer = () => window;
return (
<div>
<span>See the fixed Anchor on the right </span>
<Anchor getContainer={getContainer} offsetTop={100} targetOffset={100} style={{ position: 'fixed', right: '20px', top: '100px', width: '200px', 'z-index': '3' }}>
<Anchor.Link href="#Basic_Usage" title="Fixed Anchor" />
<Anchor.Link href="#Integrated_Usage" title="Integrated Usage" />
<Anchor.Link href="#Size" title="Size" />
<Anchor.Link href="#Rail_Theme" title="Rail Theme" />
<Anchor.Link href="#Auto_Collapse" title="Auto Collapse" />
<Anchor.Link href="#Show_Tooltip" title="Show Tooltip" />
<Anchor.Link href="#Tooltip_Position" title="Tooltip Position" />
<Anchor.Link href="#API_Reference" title="API Reference">
<Anchor.Link href="#Anchor" title="Anchor" />
<Anchor.Link href="#Anchor.Link" title="Anchor.Link" />
</Anchor.Link>
</Anchor>
</div>
);
}
Size
You can change Anchor size with size property.
Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<Anchor size="default">
<Anchor.Link href="#组件" title="组件" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
);
}Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<Anchor size="small">
<Anchor.Link href="#组件" title="组件" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
);
}Rail Theme
You can change rail color with railTheme property. Three themes are supported and the default value is primary.
Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor railTheme="primary" targetOffset={60} offsetTop={100}>
<Anchor.Link href="#尺寸" title="尺寸" />
<Anchor.Link href="#滑轨主题" title="滑轨主题" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
</div>
);
}Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor railTheme="tertiary" targetOffset={60} offsetTop={100}>
<Anchor.Link href="#尺寸" title="尺寸" />
<Anchor.Link href="#滑轨主题" title="滑轨主题" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
</div>
);
}Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor railTheme="muted" targetOffset={60} offsetTop={100}>
<Anchor.Link href="#尺寸" title="尺寸" />
<Anchor.Link href="#滑轨主题" title="滑轨主题" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
</div>
);
}Auto Collapse
Anchor can dynamically display child links with autoCollapse property. The default is false.
Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor autoCollapse targetOffset={60} offsetTop={100}>
<Anchor.Link href="#动态展示" title="1. 动态展示">
<Anchor.Link href="#组件" title="1.1 组件">
<Anchor.Link href="#头像" title="1.1.1 Avatar" />
<Anchor.Link href="#按钮" title="1.1.2 Button" />
<Anchor.Link href="#图标" title="1.1.3 Icon" />
</Anchor.Link>
<Anchor.Link href="#物料" title="1.2 物料" />
<Anchor.Link href="#主题商店" title="1.3 主题商店" />
</Anchor.Link>
<Anchor.Link href="#设计语言" title="2. 设计语言" />
</Anchor>
</div>
);
}Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor autoCollapse={false} targetOffset={60} offsetTop={100}>
<Anchor.Link href="#动态展示" title="1. 动态展示">
<Anchor.Link href="#组件" title="1.1 组件">
<Anchor.Link href="#头像" title="1.1.1 Avatar" />
<Anchor.Link href="#按钮" title="1.1.2 Button" />
<Anchor.Link href="#图标" title="1.1.3 Icon" />
</Anchor.Link>
<Anchor.Link href="#物料" title="1.2 物料" />
<Anchor.Link href="#主题商店" title="1.3 主题商店" />
</Anchor.Link>
<Anchor.Link href="#设计语言" title="2. 设计语言" />
</Anchor>
</div>
);
}Show Tooltip
showTooltip can display the title of link when it exceeds the max-width. The default value is false.
Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor showTooltip targetOffset={60} offsetTop={100}>
<Anchor.Link href="#显示工具提示" title="工具提示是一个有用的工具,它可以在文字缩略时展示全部内容。" />
<Anchor.Link href="#组件" title="组件" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
</div>
);
}Tooltip Position
You can change the Tooltip position with position property. It only works when showTooltip is true.
Code
import { Anchor } from '@fibrous/semi-ui-solid';
export default function AnchorDemo() {
return (
<div>
<Anchor showTooltip position="right" targetOffset={60} offsetTop={100}>
<Anchor.Link href="#工具提示位置" title="工具提示是一个有用的工具,它可以在文字缩略时展示全部内容。" />
<Anchor.Link href="#组件" title="组件" />
<Anchor.Link href="#设计语言" title="设计语言" />
<Anchor.Link href="#物料平台" title="物料平台" />
<Anchor.Link href="#主题商店" title="主题商店" />
</Anchor>
</div>
);
}Custom Scroll Position
scrollIntoViewOptions adjusts where the target ends up in the container after a link is clicked. Its type is the Options of scroll-into-view-if-needed: block, inline, scrollMode, boundary and skipOverflowHiddenElements. Without it block is start, which scrolls the target to the top of the container.
scrollMotionstill decides whether the scroll is animated (behavior), andtargetOffsetstill shifts the positionblockproduces, when passed together withscrollIntoViewOptions.- Only the innermost vertically scrollable container is scrolled; the horizontal position is adjusted only when
inlineis passed.
Code
import { For } from 'solid-js';
import { Anchor } from '@fibrous/semi-ui-solid';
const sections = ['section-a', 'section-b', 'section-c'];
export default function AnchorDemo() {
return (
<div style={{ display: 'flex', gap: '24px' }}>
<Anchor getContainer={() => document.getElementById('scroll-box')} scrollMotion scrollIntoViewOptions={{ block: 'center' }} style={{ width: '160px' }}>
<For each={sections}>{(id, index) => <Anchor.Link href={`#${id}`} title={`章节 ${index() + 1}`} />}</For>
</Anchor>
{/* 可聚焦,键盘也能滚动这个容器 */}
<section id="scroll-box" aria-label="章节" tabIndex={0} style={{ height: '240px', width: '320px', overflow: 'auto', border: '1px solid #ddd' }}>
<For each={sections}>
{(id, index) => (
<div id={id} style={{ height: '200px', padding: '8px' }}>
点击链接后,章节 {index() + 1} 会滚动到容器中间
</div>
)}
</For>
</section>
</div>
);
}API Reference
Anchor
Props
| Property | Description | Type | Default |
|---|---|---|---|
| autoCollapse | Whether child links are shown dynamically: only the branch that holds the highlighted link is expanded. | boolean | false |
| defaultAnchor | Link highlighted on mount. It does not call onChange or onClick. | string | "" |
| getContainer | Returns the scrolling container, window when omitted. Returning null also falls back to window. | Type() => HTMLElement | Window | null | Type() => window |
| maxHeight | max-height of the component, with a scrollbar when exceeded. This prop overrides max-height in style. | string | number | "750px" |
| maxWidth | max-width of the component, truncating when exceeded. This prop overrides max-width in style. | string | number | "200px" |
| offsetTop | Offset from the top of the container at which the current link switches while content scrolls. | number | 0 |
| onChange | Called when the highlighted link changes, with the current and the previous link. | Type(currentLink: string, previousLink: string) => void | - |
| onClick | Called when a link is clicked or activated with Enter, with the native MouseEvent or KeyboardEvent and the current link. | Type(e: AnchorClickEvent, currentLink: string) => void | - |
| position | Position of the Tooltip when showTooltip is on, with the same values as the Tooltip position. | Position | - |
| railTheme | Theme of the rail: primary, tertiary or muted. | 'primary' | 'tertiary' | 'muted' | "primary" |
| scrollIntoViewOptions | Options passed to scroll-into-view-if-needed when a link is clicked, combined with scrollMotion and targetOffset. Without block the value is start; the horizontal position changes only when inline is passed. | AnchorBaseProps['scrollIntoViewOptions'] | - |
| scrollMotion | Whether scrolling after a click is animated (behavior is smooth). | boolean | false |
| showTooltip | Whether a Tooltip shows when the text is truncated, with its options: type is the popup component, tooltip (default) or popover, and opts are passed to it. | boolean | ShowTooltip | false |
| size | Size of the anchor: small or default. | 'small' | 'default' | "default" |
| targetOffset | Distance between the target and the top of the container when scrolling ends. | number | 0 |
class, style, ref and native attributes (such as data-* and aria-*) land on the root element (role="navigation"). onClick is a component callback, not a native click listener on the root element. maxWidth and maxHeight override the max-width and max-height in style.
Anchor.Link
Props
| Property | Description | Type | Default |
|---|---|---|---|
| disabled | Whether the link is disabled and ignores clicks. | boolean | - |
| href | Target of the link. A value starting with # is looked up by element id, anything else as a CSS selector. Defaults to # when unset. | string | - |
| title | Text of the link, which can be a node. When showTooltip is off and the value is a non-empty string, it is also the native title. | JSX.Element | - |
class, style, ref and native attributes (such as data-*) land on the outermost div (role="listitem") of the link.
Content Guidelines
- Write in sentence case
- Keep it concise and avoid line breaks
Design Tokens
| Sass variable | Value | Usage |
|---|---|---|
| $transition_duration-anchor_title-text | var(--semi-transition_duration-none) | 锚点标题文字-文字-动画持续时间 |
| $transition_function-anchor_title-text | var(--semi-transition_function-easeIn) | 锚点标题文字-文字-过渡曲线 |
| $transition_delay-anchor_title-text | var(--semi-transition_delay-none) | 锚点标题文字-文字-延迟时间 |
| $transform_scale-anchor_title-text | var(--semi-transform_scale-none) | 锚点-放大 |
| $color-anchor_slide_default-bg-default | var(--semi-color-border) | 滑轨背景颜色 |
| $color-anchor_slide_primary-bg-active | var(--semi-color-primary) | 选中颜色 - Primary |
| $color-anchor_slide_tertiary-bg-active | var(--semi-color-tertiary) | 选中颜色 - Tietrary |
| $color-anchor_title-text-default | var(--semi-color-text-2) | 文字颜色 - 未选中 |
| $color-anchor_title-text-hover | var(--semi-color-tertiary-hover) | 文字颜色 - 未选中悬浮态 |
| $color-anchor_title_active-text-hover | $color-anchor_title-text-hover | 文字颜色 - 选中悬浮态 |
| $color-anchor_title-text-active | var(--semi-color-text-0) | 文字颜色 - 选中 |
| $color-anchor_title-text-disabled | var(--semi-color-disabled-text) | 文字颜色 - 禁用 |
| $color-anchor_title-bg-default | transparent | 背景色 |
| $color-anchor_title-bg-active | transparent | 背景色 - 选中 |
| $color-anchor_title-outline-focus | $color-focus-ring | 轮廓 - 聚焦 |
| $spacing-anchor_slide-left | $spacing-none | 滑轨左侧位置 |
| $spacing-anchor_slide-top | $spacing-none | 滑轨顶部位置 |
| $spacing-anchor_slide_default-Y | $spacing-extra-tight | 选项间距 - 默认 |
| $spacing-anchor_slide_small-Y | $spacing-extra-tight | 选项间距 - 紧凑 |
| $spacing-anchor_link_title-paddingTop | $spacing-extra-tight | 选项文字顶部内边距 |
| $spacing-anchor_link_title-paddingBottom | $spacing-extra-tight | 选项文字底部内边距 |
| $width-anchor_slide_default | 2px | 滑轨宽度 |
| $height-anchor_slide_default | 20px | 选项高度 - 默认 |
| $height-anchor_slide_small | 16px | 选项高度 - 小尺寸 |
| $radius-anchor_slide | 1px | 滑轨圆角 |
| $width-anchor-outline | $width-focus-ring | anchor轮廓宽度 |
| $width-anchor-outlineOffset | -2px | anchor轮廓 outline-offset 宽度 |
| $width-anchor-outline_border_radius | 3px | anchor轮廓圆角 |
FAQ
- Why didn't my link highlight and slide to follow?
Check whether you can scroll to the specified position by clicking the anchor:- No, it means there is a problem with the id. check whether the id exists in the document;
- Yes, it may be that the scrolling container is not set correctly to ensure that the content of the document is wrapped in the scrolling container. The default scrolling container is window. If your container is a div of .my-container, you should set the scrolling container to this div.
import { Anchor } from '@fibrous/semi-ui-solid';
// This is the container of the document content, not of Anchor: the current id is computed against it
const getContainer = () => document.querySelector<HTMLElement>('.my-container');
function App() {
return (
<Anchor getContainer={getContainer}>
{/* Links */}
</Anchor>
);
}