> SYSTEM / CORE / COMPONENTS / BASIC-UI _ « 返回索引
🎨

基础 UI 组件库

常用的基础界面元素,包括按钮、输入框、卡片等。

组件配额 5
状态 ACTIVE

01. 玻璃拟态卡片 (Glass Card)

具有磨砂玻璃质感的卡片容器,支持背景模糊和半透明边框。

💎

Glass Card

Interactive Component

玻璃拟态 (Glassmorphism) 是一种现代 UI 设计趋势,通过模拟磨砂玻璃的物理特性(如模糊、反射和透明度)来创造深度的层次感。

Blur 12px
Opacity 3%
---
interface Props {
  class?: string;
  title?: string;
  icon?: string;
  subtitle?: string;
}

const { 
  class: className, 
  title = "Glass Card", 
  icon = "💎", 
  subtitle = "Interactive Component" 
} = Astro.props;
---

<div class={`glass-card-preview ${className}`}>
  { (Astro.slots.has('header') || title || icon) && (
    <div class="card-header">
      <slot name="header">
        <div class="header-content">
          {icon && <span class="header-icon">{icon}</span>}
          {title && <h3 class="header-title">{title}</h3>}
        </div>
      </slot>
    </div>
  )}

  { (Astro.slots.has('subheader') || subtitle) && (
    <div class="card-subheader">
      <slot name="subheader">
        <span class="subheader-text">{subtitle}</span>
      </slot>
    </div>
  )}

  <div class="card-content">
    <slot>
      <div class="card-demo-content">
        <p>玻璃拟态 (Glassmorphism) 是一种现代 UI 设计趋势,通过模拟磨砂玻璃的物理特性(如模糊、反射和透明度)来创造深度的层次感。</p>
        <div class="demo-stats">
          <div class="stat">
            <span class="label">Blur</span>
            <span class="value">12px</span>
          </div>
          <div class="stat">
            <span class="label">Opacity</span>
            <span class="value">3%</span>
          </div>
        </div>
      </div>
    </slot>
  </div>

  { (Astro.slots.has('footer') || true) && (
    <div class="card-footer">
      <slot name="footer">
        <div class="footer-demo-content">
          <span class="footer-tag">Design System</span>
          <span class="footer-version">v1.0.4</span>
        </div>
      </slot>
    </div>
  )}
</div>

<style>
  .glass-card-preview {
    background: var(--glass-bg);
    backdrop-filter: var(--glass-blur);
    -webkit-backdrop-filter: var(--glass-blur);
    border: var(--glass-border);
    border-radius: 16px;
    padding: 1.25rem;
    box-shadow: var(--glass-shadow);
    width: 100%;
    max-width: 320px;
    transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
    display: flex;
    flex-direction: column;
    gap: 0.75rem;
    position: relative;
    overflow: hidden;
  }

  .glass-card-preview::before {
    content: '';
    position: absolute;
    top: 0;
    left: -100%;
    width: 100%;
    height: 100%;
    background: linear-gradient(
      90deg,
      transparent,
      rgba(255, 255, 255, 0.3),
      transparent
    );
    transition: 0.5s;
  }

  .glass-card-preview:hover::before {
    left: 100%;
  }

  .glass-card-preview:hover {
    transform: translateY(-5px);
    border-color: var(--color-primary-start);
    box-shadow: 0 12px 30px rgba(0, 0, 0, 0.08);
  }

  /* Header Styles */
  .card-header {
    border-bottom: 1px solid rgba(0, 0, 0, 0.05);
    padding-bottom: 0.75rem;
  }

  .header-content {
    display: flex;
    align-items: center;
    gap: 0.6rem;
  }

  .header-icon {
    font-size: 1.2rem;
    filter: drop-shadow(0 0 8px rgba(var(--color-primary-rgb), 0.3));
  }

  .header-title {
    margin: 0;
    font-size: 1.05rem;
    font-weight: 600;
    color: var(--color-text-title);
    letter-spacing: 0.5px;
  }

  /* Subheader Styles */
  .card-subheader {
    font-size: 0.8rem;
    color: var(--color-neutral);
    margin-top: -0.25rem;
    font-family: var(--font-mono);
  }

  /* Content Styles */
  .card-content {
    flex: 1;
    color: var(--color-text-body);
    font-size: 0.9rem;
    line-height: 1.6;
    margin: 0.5rem 0;
  }

  /* Footer Styles */
  .card-footer {
    border-top: 1px solid rgba(0, 0, 0, 0.05);
    padding-top: 0.75rem;
    margin-top: 0.25rem;
    font-size: 0.85rem;
    color: var(--color-neutral);
  }

  .footer-demo-content {
    display: flex;
    justify-content: space-between;
    align-items: center;
  }

  .footer-tag {
    color: var(--color-primary-start);
    font-weight: 500;
  }

  .footer-version {
    opacity: 0.6;
    font-family: var(--font-mono);
    font-size: 0.75rem;
  }

  .card-demo-content {
    display: flex;
    flex-direction: column;
    gap: 1.25rem;
  }

  .demo-stats {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 1rem;
    padding: 0.75rem;
    background: rgba(var(--color-primary-rgb), 0.03);
    border-radius: 8px;
    border: 1px solid rgba(var(--color-primary-rgb), 0.05);
  }

  .stat {
    display: flex;
    flex-direction: column;
    gap: 0.25rem;
  }

  .stat .label {
    font-size: 0.65rem;
    text-transform: uppercase;
    letter-spacing: 1px;
    color: var(--color-neutral);
  }

  .stat .value {
    font-size: 0.9rem;
    font-weight: 600;
    color: var(--color-primary-start);
    font-family: var(--font-mono);
  }
</style>

组件特性

  • 结构化布局:内置 Header、Subheader、Content 和 Footer 区域。
  • 磨砂玻璃效果:利用 backdrop-filter: blur() 实现。
  • 插槽灵活性:支持通过 slot="header"slot="subheader"slot="footer" 自定义各个区域的内容。
  • 悬停交互:平滑的上移和阴影加深效果。

视觉细节

建议在具有彩色或复杂背景的容器中使用,以突出玻璃的透明感。可以使用内置的 titleicon 属性快速构建卡片头部。

Attributes

参数 说明 类型 默认值
title 卡片顶部标题 `string` -
icon 标题旁的图标 (支持 Emoji 或图标组件) `string` -
subtitle 标题下方的副标题 `string` -
class 自定义样式类名 `string` ''

02. 新拟态按钮 (Neumorphic Button)

具有独特光影反馈的按钮,支持多种类型、尺寸和形状,内置扫光动效。

---
interface Props {
  text?: string;
  type?: 'primary' | 'secondary' | 'outline' | 'ghost';
  size?: 'sm' | 'md' | 'lg';
  shape?: 'square' | 'rounded' | 'pill';
  class?: string;
}

const { 
  text = "PUSH_ME", 
  type = 'primary', 
  size = 'md', 
  shape = 'rounded',
  class: className 
} = Astro.props;
---

<button class:list={[
  'neo-button-preview',
  `type-${type}`,
  `size-${size}`,
  `shape-${shape}`,
  className
]}>
  <span class="btn-text">{text}</span>
  <div class="btn-glitch"></div>
</button>

<style>
  .neo-button-preview {
    position: relative;
    border: none;
    font-family: var(--font-mono);
    font-weight: 700;
    letter-spacing: 1px;
    cursor: pointer;
    overflow: hidden;
    transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
    display: inline-flex;
    align-items: center;
    justify-content: center;
    white-space: nowrap;
    outline: none;
  }

  /* Sizes */
  .size-sm {
    padding: 0.4rem 1rem;
    font-size: 0.75rem;
  }
  .size-md {
    padding: 0.7rem 1.75rem;
    font-size: 0.9rem;
  }
  .size-lg {
    padding: 1rem 2.5rem;
    font-size: 1.1rem;
  }

  /* Shapes */
  .shape-square { border-radius: 0; }
  .shape-rounded { border-radius: 6px; }
  .shape-pill { border-radius: 9999px; }

  /* Types */
  .type-primary {
    background: var(--color-primary-start);
    color: white;
    box-shadow: 0 4px 15px rgba(var(--color-primary-rgb), 0.3);
  }
  .type-primary:hover {
    background: var(--color-primary-end);
    box-shadow: 0 6px 20px rgba(var(--color-primary-rgb), 0.4);
    transform: translateY(-2px);
  }

  .type-secondary {
    background: rgba(var(--color-primary-rgb), 0.1);
    color: var(--color-primary-start);
    border: 1px solid rgba(var(--color-primary-rgb), 0.2);
  }
  .type-secondary:hover {
    background: rgba(var(--color-primary-rgb), 0.15);
    border-color: var(--color-primary-start);
    transform: translateY(-2px);
  }

  .type-outline {
    background: transparent;
    color: var(--color-primary-start);
    border: 2px solid var(--color-primary-start);
  }
  .type-outline:hover {
    background: var(--color-primary-start);
    color: white;
    transform: translateY(-2px);
  }

  .type-ghost {
    background: transparent;
    color: var(--color-text-body);
  }
  .type-ghost:hover {
    background: rgba(0, 0, 0, 0.05);
    color: var(--color-primary-start);
  }

  .neo-button-preview:active {
    transform: translateY(0) scale(0.98);
  }

  .btn-glitch {
    position: absolute;
    top: 0;
    left: -100%;
    width: 100%;
    height: 100%;
    background: linear-gradient(
      90deg,
      transparent,
      rgba(255, 255, 255, 0.3),
      transparent
    );
    transition: 0.5s;
  }

  .neo-button-preview:hover .btn-glitch {
    left: 100%;
  }

  .btn-text {
    position: relative;
    z-index: 1;
  }
</style>

组件特性

  • 多样化风格:预设四种核心类型,满足不同场景的权重需求。
  • 扫光动效:悬停时触发平滑的扫光效果,增强科技感。
  • 交互反馈:内置活跃态(Active)缩放效果,模拟真实的按压触感。
  • 灵活布局:支持三种常用尺寸和三种边框形状,高度可配置。

使用建议

推荐在深色或具有玻璃质感的容器中使用,以获得最佳的视觉表现。primary 类型自带发光阴影,适合作为页面的 Call-to-Action 按钮。

Attributes

参数 说明 类型 默认值
text 按钮显示的文字内容 `string` 'PUSH_ME'
type 按钮风格类型 `'primary' | 'secondary' | 'outline' | 'ghost'` 'primary'
size 按钮尺寸大小 `'sm' | 'md' | 'lg'` 'md'
shape 按钮圆角形状 `'square' | 'rounded' | 'pill'` 'rounded'
class 自定义样式类名 `string` ''

03. 赛博开关 (Cyber Toggle)

具有未来科技感的二进制切换开关,支持多种尺寸和禁用状态。

SYSTEM_CORE
---
interface Props {
  label?: string;
  checked?: boolean;
  size?: 'sm' | 'md' | 'lg';
  disabled?: boolean;
  class?: string;
}

const { 
  label = "SYSTEM_CORE", 
  checked = true, 
  size = 'md',
  disabled = false,
  class: className 
} = Astro.props;
---

<div class:list={["cyber-toggle-container", size, { disabled }, className]}>
  {label && <span class="toggle-label">{label}</span>}
  <label class="toggle-wrapper">
    <input type="checkbox" checked={checked} disabled={disabled} />
    <div class="toggle-track">
      <div class="toggle-thumb">
        <div class="thumb-core"></div>
      </div>
      <div class="track-glitch"></div>
    </div>
  </label>
</div>

<style>
  .cyber-toggle-container {
    display: inline-flex;
    align-items: center;
    gap: 1rem;
    font-family: var(--font-mono);
    user-select: none;
  }

  .toggle-label {
    font-size: 0.85rem;
    font-weight: 700;
    color: var(--color-text-title);
    letter-spacing: 1px;
    text-transform: uppercase;
  }

  .toggle-wrapper {
    position: relative;
    cursor: pointer;
    display: block;
  }

  .toggle-wrapper input {
    position: absolute;
    opacity: 0;
    width: 0;
    height: 0;
  }

  /* Track Styling */
  .toggle-track {
    position: relative;
    width: 54px;
    height: 28px;
    background: rgba(0, 0, 0, 0.4);
    border: 1px solid rgba(var(--color-primary-rgb), 0.3);
    border-radius: 4px;
    transition: all 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275);
    overflow: hidden;
    box-shadow: inset 0 2px 5px rgba(0, 0, 0, 0.5);
  }

  .toggle-wrapper input:checked + .toggle-track {
    background: rgba(var(--color-primary-rgb), 0.1);
    border-color: var(--color-primary-start);
    box-shadow: 0 0 15px rgba(var(--color-primary-rgb), 0.2);
  }

  /* Thumb Styling */
  .toggle-thumb {
    position: absolute;
    top: 3px;
    left: 3px;
    width: 20px;
    height: 20px;
    background: #2a2a2a;
    border: 1px solid #444;
    border-radius: 2px;
    transition: all 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 2;
  }

  .thumb-core {
    width: 8px;
    height: 8px;
    background: #666;
    border-radius: 1px;
    transition: all 0.3s ease;
  }

  .toggle-wrapper input:checked + .toggle-track .toggle-thumb {
    transform: translateX(26px);
    background: var(--color-primary-start);
    border-color: #fff;
    box-shadow: 0 0 10px var(--color-primary-start);
  }

  .toggle-wrapper input:checked + .toggle-track .thumb-core {
    background: #fff;
    box-shadow: 0 0 5px #fff;
  }

  /* Glitch Effect on Track */
  .track-glitch {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: linear-gradient(90deg, transparent, rgba(var(--color-primary-rgb), 0.2), transparent);
    transform: translateX(-100%);
    transition: transform 0.6s ease;
  }

  .toggle-wrapper:hover .track-glitch {
    transform: translateX(100%);
  }

  /* Size Variations */
  .sm .toggle-track { width: 44px; height: 22px; }
  .sm .toggle-thumb { width: 14px; height: 14px; top: 3px; left: 3px; }
  .sm .toggle-wrapper input:checked + .toggle-track .toggle-thumb { transform: translateX(22px); }
  .sm .toggle-label { font-size: 0.7rem; }

  .lg .toggle-track { width: 64px; height: 34px; }
  .lg .toggle-thumb { width: 26px; height: 26px; top: 3px; left: 3px; }
  .lg .toggle-wrapper input:checked + .toggle-track .toggle-thumb { transform: translateX(30px); }
  .lg .toggle-label { font-size: 1rem; }

  /* Disabled State */
  .disabled {
    opacity: 0.5;
    pointer-events: none;
  }
  .disabled .toggle-track {
    border-color: #333;
    background: #111;
  }
</style>

组件特性

  • 工业设计:采用硬朗的方角设计,区别于传统的圆润风格,更具工业和科幻感。
  • 动态反馈:开关切换时带有平滑的位移动效,并伴有核心发光效果。
  • 扫描特效:鼠标悬停时,轨道内部会触发一层流光扫描特效。
  • 多尺寸适配:预设了三种尺寸,能够灵活适配从侧边栏到主面板的不同布局需求。

使用建议

推荐在深色模式或具有科技感的 UI 界面中使用。作为核心功能的开关时,建议搭配 lg 尺寸以增强视觉引导。

Attributes

参数 说明 类型 默认值
label 开关旁的标签文字 `string` 'SYSTEM_CORE'
checked 开关的初始状态 `boolean` true
size 开关的尺寸 `'sm' | 'md' | 'lg'` 'md'
disabled 是否禁用开关 `boolean` false
class 自定义样式类名 `string` ''

04. 赛博徽章 (Cyber Badge)

极小尺寸的高信息密度标签,支持多种语义颜色和交互特效。

STABLE
---
interface Props {
  text?: string;
  type?: 'primary' | 'success' | 'warning' | 'error' | 'neutral';
  variant?: 'solid' | 'outline' | 'glitch';
  size?: 'xs' | 'sm' | 'md';
  class?: string;
}

const { 
  text = "STABLE", 
  type = 'primary', 
  variant = 'outline',
  size = 'sm',
  class: className 
} = Astro.props;
---

<span class:list={["cyber-badge", type, variant, size, className]}>
  <span class="badge-content">{text}</span>
  {variant === 'glitch' && <span class="badge-glitch" aria-hidden="true">{text}</span>}
</span>

<style>
  .cyber-badge {
    display: inline-flex;
    align-items: center;
    padding: 2px 10px;
    font-family: var(--font-mono);
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 1px;
    border-radius: 2px;
    position: relative;
    white-space: nowrap;
    user-select: none;
    font-size: 0.7rem;
  }

  /* Sizes */
  .xs { padding: 1px 6px; font-size: 0.6rem; }
  .sm { padding: 2px 10px; font-size: 0.7rem; }
  .md { padding: 4px 14px; font-size: 0.8rem; }

  /* Types (Colors) */
  .primary { 
    --badge-color: var(--color-primary-start); 
    --badge-rgb: var(--color-primary-rgb);
  }
  .success { 
    --badge-color: #10b981; 
    --badge-rgb: 16, 185, 129;
  }
  .warning { 
    --badge-color: #f59e0b; 
    --badge-rgb: 245, 158, 11;
  }
  .error { 
    --badge-color: #ef4444; 
    --badge-rgb: 239, 68, 68;
  }
  .neutral { 
    --badge-color: var(--color-neutral); 
    --badge-rgb: 156, 163, 175;
  }

  /* Variants */
  .solid {
    background: var(--badge-color);
    color: #000;
    box-shadow: 0 0 10px rgba(var(--badge-rgb), 0.3);
  }

  .outline {
    background: rgba(var(--badge-rgb), 0.1);
    border: 1px solid var(--badge-color);
    color: var(--badge-color);
    box-shadow: inset 0 0 5px rgba(var(--badge-rgb), 0.2);
  }

  .glitch {
    background: transparent;
    border: 1px solid var(--badge-color);
    color: var(--badge-color);
    overflow: hidden;
  }

  .badge-glitch {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: var(--badge-color);
    color: #000;
    display: flex;
    align-items: center;
    justify-content: center;
    transform: translateX(-101%);
    transition: transform 0.3s cubic-bezier(0.7, 0, 0.3, 1);
  }

  .cyber-badge:hover .badge-glitch {
    transform: translateX(0);
  }

  .badge-content {
    position: relative;
    z-index: 1;
  }
</style>

组件特性

  • 工业语义化:内置五种核心语义颜色,能够清晰传递系统状态信息。
  • Glitch 特效glitch 变体在悬停时会触发一个覆盖式的色块滑动效果,增加交互的动感。
  • 紧凑布局:专为高密度信息流设计,即使在 xs 尺寸下也能保持极佳的可读性。
  • 等宽字体:强制使用等宽字体,确保在不同文字内容下徽章的视觉重心保持一致。

使用建议

推荐用于文章标签、代码版本号标记或监控面板的状态显示。在列表项中使用时,建议保持 size="sm" 以维持视觉平衡。

Attributes

参数 说明 类型 默认值
text 徽章显示的文字内容 `string` 'STABLE'
type 语义化颜色类型 `'primary' | 'success' | 'warning' | 'error' | 'neutral'` 'primary'
variant 视觉风格:实心、轮廓或带有 Glitch 悬停特效 `'solid' | 'outline' | 'glitch'` 'outline'
size 徽章尺寸 `'xs' | 'sm' | 'md'` 'sm'
class 自定义样式类名 `string` ''

05. 全息头像 (Hologram Avatar)

具有全息投影质感的头像组件,支持扫描线、外发光环和故障特效。

---
interface Props {
  src?: string;
  size?: 'sm' | 'md' | 'lg';
  glowColor?: string;
  scanline?: boolean;
  class?: string;
}

const { 
  src = "https://images.unsplash.com/photo-1535713875002-d1d0cf377fde?auto=format&fit=crop&w=200&h=200", 
  size = 'md', 
  glowColor = "var(--color-primary-start)",
  scanline = true,
  class: className 
} = Astro.props;

const sizeMap = {
  sm: '60px',
  md: '100px',
  lg: '160px'
};
---

<div class:list={["hologram-avatar-container", size, className]} style={{ '--glow-color': glowColor, '--avatar-size': sizeMap[size] }}>
  <div class="avatar-wrapper">
    <div class="avatar-image" style={{ backgroundImage: `url(${src})` }}></div>
    <div class="hologram-layer"></div>
    {scanline && <div class="scanline-layer"></div>}
    <div class="glitch-layer"></div>
  </div>
  <div class="avatar-ring"></div>
  <div class="avatar-glow"></div>
</div>

<style>
  .hologram-avatar-container {
    position: relative;
    width: var(--avatar-size);
    height: var(--avatar-size);
    display: flex;
    align-items: center;
    justify-content: center;
  }

  .avatar-wrapper {
    position: relative;
    width: 100%;
    height: 100%;
    border-radius: 50%;
    overflow: hidden;
    z-index: 2;
    border: 2px solid rgba(255, 255, 255, 0.1);
  }

  .avatar-image {
    width: 100%;
    height: 100%;
    background-size: cover;
    background-position: center;
    filter: saturate(0.5) contrast(1.2) brightness(1.1) sepia(0.2);
  }

  /* Hologram Effect */
  .hologram-layer {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: linear-gradient(
      rgba(var(--color-primary-rgb), 0.2) 0%,
      transparent 100%
    );
    mix-blend-mode: screen;
    pointer-events: none;
  }

  .scanline-layer {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: linear-gradient(
      to bottom,
      transparent,
      rgba(var(--color-primary-rgb), 0.1) 50%,
      transparent
    );
    background-size: 100% 4px;
    animation: scanMove 3s linear infinite;
    pointer-events: none;
  }

  @keyframes scanMove {
    from { background-position: 0 0; }
    to { background-position: 0 100%; }
  }

  /* Ring and Glow */
  .avatar-ring {
    position: absolute;
    top: -5px;
    left: -5px;
    right: -5px;
    bottom: -5px;
    border: 1px solid var(--glow-color);
    border-radius: 50%;
    opacity: 0.5;
    animation: rotate 10s linear infinite;
    z-index: 1;
  }

  .avatar-ring::after {
    content: '';
    position: absolute;
    top: -2px;
    left: 50%;
    width: 4px;
    height: 4px;
    background: #fff;
    border-radius: 50%;
    box-shadow: 0 0 10px #fff;
  }

  .avatar-glow {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: var(--glow-color);
    filter: blur(25px);
    opacity: 0.2;
    border-radius: 50%;
    z-index: 0;
  }

  @keyframes rotate {
    from { transform: rotate(0deg); }
    to { transform: rotate(360deg); }
  }

  /* Glitch on Hover */
  .hologram-avatar-container:hover .avatar-image {
    animation: glitch 0.2s infinite;
  }

  @keyframes glitch {
    0% { transform: translate(0); }
    20% { transform: translate(-2px, 1px); filter: hue-rotate(90deg); }
    40% { transform: translate(2px, -1px); filter: hue-rotate(180deg); }
    60% { transform: translate(-1px, 2px); filter: hue-rotate(270deg); }
    80% { transform: translate(1px, -2px); }
    100% { transform: translate(0); }
  }
</style>

组件特性

  • 全息质感:通过色彩偏移(Sepia)、对比度调整和半透明遮罩,模拟全息影像的半透明和不稳定感。
  • 动态光环:头像外围环绕一个持续旋转的能量环,带有一个亮白色的“轨道卫星”点。
  • 故障交互:鼠标悬停时,头像会触发强烈的 Glitch 故障动效,包括位置抖动和色相旋转。
  • 扫描动画:内置垂直移动的扫描线,增强了老式科幻界面的临场感。

使用建议

推荐在侧边栏用户信息、评论系统头像或 AI 对话框中使用。由于全息效果会降低图片的色彩饱和度,建议使用对比度较高的原始图片以获得最佳效果。

Attributes

参数 说明 类型 默认值
src 图片源地址 `string` -
size 头像尺寸 `'sm' | 'md' | 'lg'` 'md'
glowColor 外发光颜色 `string` 'var(--color-primary-start)'
scanline 是否显示扫描线 `boolean` true
class 自定义样式类名 `string` ''