Skip to content
On this page

骨架屏 Skeleton

在需要等待加载内容的位置设置一个骨架屏,某些场景下比 Loading 的视觉效果更好。

基础用法

基础的骨架效果

<template>
  <b-skeleton></b-skeleton>
</template>
<template>
  <b-skeleton></b-skeleton>
</template>

更多参数

可以配置骨架屏段落数量,以便更接近真实渲染效果。显示的数量会比传入的数量多 1,首行会被渲染一个长度 33% 的段首。

<template>
  <b-skeleton :rows="5"></b-skeleton>
</template>
<template>
  <b-skeleton :rows="5"></b-skeleton>
</template>

动画效果

可以显示动画效果

<template>
  <b-skeleton animation></b-skeleton>
</template>
<template>
  <b-skeleton animation></b-skeleton>
</template>

自定义

可以使用slot插槽来自己设定模板,可以根据真实dom来构建差不多的骨架

<template>
  <b-skeleton style="width: 240px" animation>
    <template #template>
      <b-skeleton-item variant="image" style="width: 240px; height: 240px" />
      <div style="padding: 14px">
        <b-skeleton-item variant="p" style="width: 50%" />
        <div flex="main:justify cross:center">
          <b-skeleton-item variant="text" style="margin-right: 16px" />
          <b-skeleton-item variant="text" style="width: 30%" />
        </div>
      </div>
    </template>
  </b-skeleton>
</template>
<template>
  <b-skeleton style="width: 240px" animation>
    <template #template>
      <b-skeleton-item variant="image" style="width: 240px; height: 240px" />
      <div style="padding: 14px">
        <b-skeleton-item variant="p" style="width: 50%" />
        <div flex="main:justify cross:center">
          <b-skeleton-item variant="text" style="margin-right: 16px" />
          <b-skeleton-item variant="text" style="width: 30%" />
        </div>
      </div>
    </template>
  </b-skeleton>
</template>

Loading 加载

loading结束后加载真实的ui,通过slot设置之后的ui

用户信息

用户信息内容

用户信息内容

用户信息内容

2024-09-04

<template>
  <div>
    <div class="mb-15">
      <b-button @click="show">2s 后显示</b-button>
    </div>
    <b-skeleton style="width: 350px" :loading="loading" animation>
      <template #template>
        <div flex="cross:center" style="margin-bottom: 8px">
          <b-skeleton-item variant="circle" style="width: 36px; margin-right: 8px" />
          <div style="width: 200px">
            <div flex="main:justify cross:center">
              <b-skeleton-item variant="text" style="margin-right: 16px" />
              <b-skeleton-item variant="text" style="width: 30%" />
            </div>
          </div>
        </div>
        <b-skeleton />
      </template>
      <template #default>
        <div style="width: 350px">
          <div flex="cross:center" style="margin-bottom: 8px">
            <b-skeleton-item variant="circle" style="width: 36px; margin-right: 8px" />
            <div style="width: 200px">用户信息</div>
          </div>
          <p>用户信息内容</p>
          <p>用户信息内容</p>
          <p>用户信息内容</p>
          <p>{{ currentDate }}</p>
        </div>
      </template>
    </b-skeleton>
  </div>
</template>

<script setup lang="ts">
import { ref } from 'vue'
import dayjs from 'dayjs'

const loading = ref(false)
const currentDate = ref(dayjs().format('YYYY-MM-DD'))

function show() {
  loading.value = true
  setTimeout(() => {
    loading.value = false
  }, 2000)
}
</script>
<template>
  <div>
    <div class="mb-15">
      <b-button @click="show">2s 后显示</b-button>
    </div>
    <b-skeleton style="width: 350px" :loading="loading" animation>
      <template #template>
        <div flex="cross:center" style="margin-bottom: 8px">
          <b-skeleton-item variant="circle" style="width: 36px; margin-right: 8px" />
          <div style="width: 200px">
            <div flex="main:justify cross:center">
              <b-skeleton-item variant="text" style="margin-right: 16px" />
              <b-skeleton-item variant="text" style="width: 30%" />
            </div>
          </div>
        </div>
        <b-skeleton />
      </template>
      <template #default>
        <div style="width: 350px">
          <div flex="cross:center" style="margin-bottom: 8px">
            <b-skeleton-item variant="circle" style="width: 36px; margin-right: 8px" />
            <div style="width: 200px">用户信息</div>
          </div>
          <p>用户信息内容</p>
          <p>用户信息内容</p>
          <p>用户信息内容</p>
          <p>{{ currentDate }}</p>
        </div>
      </template>
    </b-skeleton>
  </div>
</template>

<script setup lang="ts">
import { ref } from 'vue'
import dayjs from 'dayjs'

const loading = ref(false)
const currentDate = ref(dayjs().format('YYYY-MM-DD'))

function show() {
  loading.value = true
  setTimeout(() => {
    loading.value = false
  }, 2000)
}
</script>

Skeleton Props

参数说明类型可选值默认值
animated是否使用动画booleantrue / falsefalse
count渲染多少个 template, 建议使用尽可能小的数字numberinteger1
loading是否显示真实的 DOM 结构booleantrue / falsefalse
rows骨架屏段落数量number正整数3
throttle延迟占位 DOM 渲染的时间, 单位是毫秒number正整数0

Skeleton Item Attributes

参数说明类型可选值默认值
variant当前显示的占位元素的样式Enum(string)p / text / h1 / h2 / h5 / text / caption / button / image / circle / recttext

Skeleton Slots

namedescription
default用来展示真实 UI
template用来展示自定义占位符