Skip to content

Slider 滑块 ​

Slider 从区间中选一个值,RangeSlider 用两个手柄选一段区间。两者外观一致: 圆角轨道、竖条手柄、手柄两侧的间隙、端点圆点,以及可选的刻度点与数值气泡。

  • v-model 绑定数值(Slider 为 number,RangeSlider 为 [最小值, 最大值])。
  • size 控制轨道厚度:XS 16px、S 24px、M 40px、L 56px、XL 96px(默认 XS)。
  • 拖动时手柄变细,并在其上方显示数值气泡;showValue="always" 则始终显示。
  • ticks 在轨道上标出每个可选值,centered 让 Slider 从 0 值处开始填充。
  • 两端可以放任意内容(加号 / 减号图标、文字、按钮),由 #start / #end 插槽提供。

基础用法 ​

当前值:40

vue
<script setup lang="ts">
import { ref } from "vue";
import { Slider } from "@sharpdotnut/dotsharp";

const volume = ref(40);
</script>

<template>
  <Slider v-model="volume" label="音量" />
</template>

min / max 默认 0 / 100,step 默认 1。点击轨道任意位置即可跳转,移动过程与点击后的跳转都带过渡动画; 拖动时按 step 吸附并夹在 min–max 之间。

居中零点 ​

centered 把填充原点从轨道起点移到 0(若 0 不在范围内,则取最接近的端点),用于正负对称的取值,例如亮度补偿、温度偏移。

当前值:20

vue
<script setup lang="ts">
import { ref } from "vue";
import { Slider } from "@sharpdotnut/dotsharp";

const centered = ref(20);
</script>

<template>
  <Slider v-model="centered" :min="-100" :max="100" :step="5" centered label="偏移量" />
</template>

范围滑块 ​

RangeSlider 的 v-model 是 [低位, 高位],两个手柄不会交叉;拖动 / 点击时命中的是离指针更近的手柄。 数值气泡一次只显示正在操作的那一个手柄。

两个手柄是两个独立的 role="slider",只传 label 会让它们共用同一个名字;用 labels 分别命名: labels[0] 是低位、labels[1] 是高位。

当前区间:30 – 70

vue
<script setup lang="ts">
import { ref } from "vue";
import { RangeSlider } from "@sharpdotnut/dotsharp";

const range = ref<[number, number]>([30, 70]);
</script>

<template>
  <RangeSlider v-model="range" :labels="['最低价', '最高价']" />
</template>

显示可用值 ​

ticks 在轨道上为每个可选值画一个点,选中部分用反色点、未选中部分用主题色点;端点圆点始终保留。 只有「范围 ÷ 步长」较小时才适合开启:刻度超过 20 个时组件会自动省略,避免糊成一条线。

当前值:40

vue
<script setup lang="ts">
import { ref } from "vue";
import { Slider } from "@sharpdotnut/dotsharp";

const discrete = ref(40);
</script>

<template>
  <Slider v-model="discrete" :step="20" ticks label="显示尺寸" />
</template>

数值气泡 ​

默认 showValue="drag":按下 / 拖动时手柄变细,并在上方显示当前值,松手后气泡收起。 showValue="always" 常显(示例预留了顶部空间),"never" 完全关闭。format 可以自定义气泡与 aria-valuetext 的文本。

当前值:50

vue
<script setup lang="ts">
import { ref } from "vue";
import { Slider } from "@sharpdotnut/dotsharp";

const indicator = ref(50);
</script>

<template>
  <Slider v-model="indicator" show-value="always" label="不透明度" />
</template>

两端图标 ​

#start / #end 接受任意内容。下例用 IconButton 做加减按钮,同时保留轨道上的拖动与键盘操作。

当前值:50

vue
<script setup lang="ts">
import { ref } from "vue";
import { IconButton, Slider } from "@sharpdotnut/dotsharp";
import add from "@iconify-icons/material-symbols/add";
import remove from "@iconify-icons/material-symbols/remove";

const brightness = ref(50);

function decreaseBrightness() {
  brightness.value = Math.max(0, brightness.value - 10);
}

function increaseBrightness() {
  brightness.value = Math.min(100, brightness.value + 10);
}
</script>

<template>
  <Slider v-model="brightness" label="亮度">
    <template #start>
      <IconButton
        :icon="remove"
        label="降低亮度"
        :disabled="brightness <= 0"
        @click="decreaseBrightness"
      />
    </template>
    <template #end>
      <IconButton
        :icon="add"
        label="提高亮度"
        :disabled="brightness >= 100"
        @click="increaseBrightness"
      />
    </template>
  </Slider>
</template>

插槽内容位于轨道两侧,轨道自动占据剩余宽度;放纯文字也可以(例如「小」「大」)。

尺寸 ​

五种厚度对应 XS–XL,手柄高度随轨道增长(最小 44px)。大尺寸适合强调某一个数值或触控设备。

XS · 16px
S · 24px
M · 40px
L · 56px
XL · 96px
vue
<template>
  <Slider v-model="value" size="xs" />
  <Slider v-model="value" size="s" />
  <Slider v-model="value" size="m" />
  <Slider v-model="value" size="l" />
  <Slider v-model="value" size="xl" />
</template>

禁用 ​

vue
<template>
  <Slider v-model="value" disabled label="不可用" />
</template>

禁用时手柄不可聚焦、不响应指针与键盘,整体降低不透明度。

表单校验 ​

validator 接收当前值(Slider 是 number,RangeSlider 是 [number, number]),返回 false 表示通过;返回 true 或错误文案表示不通过。默认在拖动 / 键盘改变值与失焦时校验,用 validateOn 调整;也暴露 validate() / clearValidate()。完整约定见表单指南。

API ​

Slider 属性 ​

属性类型默认值说明
v-modelnumber0当前值
minnumber0最小值
maxnumber100最大值
stepnumber1步长;值会吸附到 min + n * step
size"xs" | "s" | "m" | "l" | "xl""xs"轨道厚度(16 / 24 / 40 / 56 / 96px)
centeredbooleanfalse以 0 值为填充原点
ticksbooleanfalse显示每个可选值的刻度点(超过 20 个自动省略)
showValue"drag" | "always" | "never""drag"数值气泡的显示时机
format(value: number) => string—自定义数值文本(气泡与 aria-valuetext)
labelstring—无障碍名称
disabledbooleanfalse禁用
validator(value) => boolean | string—验证函数:false 通过,true / 字符串不通过
validateOn"input" | "blur" | ("input" | "blur")[]["input", "blur"]自动校验时机;传 [] 关闭自动校验

RangeSlider 属性 ​

与 Slider 相同,区别是 v-model 为 [number, number],且没有 centered(范围滑块固定填充两个手柄之间)。

属性类型默认值说明
v-model[number, number][0, 100]低位与高位,顺序自动归一
size"xs" | "s" | "m" | "l" | "xl""xs"轨道厚度
ticksbooleanfalse显示刻度点(超过 20 个自动省略)
showValue"drag" | "always" | "never""drag"数值气泡的显示时机
labels[string, string]—两个手柄各自的无障碍名称(低位 / 高位)

min、max、step、format、label、disabled 与 Slider 一致。

插槽 ​

插槽说明
start轨道左侧内容,常用减号图标或「小」等文字
end轨道右侧内容,常用加号图标或「大」等文字

事件 ​

事件说明
update:modelValue值变化(拖动 / 点击 / 键盘)

可访问性 ​

  • 每个手柄是 role="slider" 的可聚焦元素,带 aria-valuemin / aria-valuemax / aria-valuenow / aria-valuetext;label 会写成它的 aria-label,RangeSlider 用 labels 给两个手柄各自命名。
  • 键盘:左右 / 上下方向键按步长增减,PageUp / PageDown 按 10 倍步长,Home / End 跳到两端。
  • 拖动时使用指针捕获,指针离开组件也不会中断;轨道设置 touch-action: none,触屏上不会与页面滚动冲突。
  • 范围滑块的两个手柄各自独立聚焦;低位不会超过高位,反之亦然。