1、新建 src/components/Skeleton/index.vue, 书写骨架屏组件
<template>
<div class="skeleton shan" :style="{ width: width + 'px', height: height + 'px' }">
<div class="block" :style="{ backgroundColor: bg}"></div>
</div>
</template>
<script>
export default {
name: 'Skeleton',
props: {
width: {
type: [Number, String],
default: 100
},
height: {
type: [Number, String],
default: 60
},
bg: {
type: String,
default: '#ccc'
}
}
}
</script>
<style scoped lang="less">
.skeleton {
display: inline-block;
position: relative;
overflow: hidden;
vertical-align: middle;
.block {
width: 100%;
height: 100%;
border-radius: 2px;
}
}
.shan {
&::after {
content: "";
position: absolute;
animation: shan 1.5s ease 0s infinite;
top: 0;
width: 50%;
height: 100%;
background: linear-gradient(
to left,
rgba(255, 255, 255, 0) 0,
rgba(255, 255, 255, 0.3) 50%,
rgba(255, 255, 255, 0) 100%
);
transform: skewX(-45deg);
}
}
@keyframes shan {
0% {
left: -100%;
}
100% {
left: 120%;
}
}
</style>
2、新建 src/components/index.js,以插件形式注册为全局可用
法1:批量
export default {
install (app) {
const requireComponet = require.context('./', true, /\.vue$/)
requireComponet.keys().forEach(item => {
const moduleObj = requireComponet(item).default
console.log(moduleObj, '00')
app.component(moduleObj.name, moduleObj)
})
}
}
法2:单个
import Skeleton from './Skeleton'
export default {
install (app) {
app.component(Skeleton.name, Skeleton)
}
}
3、main.js 中 导入注册插件
import { createApp } from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'
import componentPlugins from './components'
createApp(App).use(store).use(router).use(componentPlugins).mount('#app')
4、需要的页面使用
<template>
<div class="home-category">
<ul class="menu">
<template v-if="!$store.state.category.list.length">
<li v-for="i in 9" :key="i">
<RouterLink to="/"><XtxSkeleton :width="66" :height="19"></XtxSkeleton></RouterLink>
<RouterLink to="/"><XtxSkeleton :width="66" :height="19"></XtxSkeleton></RouterLink>
<RouterLink to="/"><XtxSkeleton :width="56" :height="19"></XtxSkeleton></RouterLink>
</li>
</template>
<template v-else>
<li v-for="item in $store.state.category.list" :key="item.id">
<RouterLink to="/">{{item.name}}</RouterLink>
<template v-if="item.children.length > 0">
<RouterLink to="/" v-for="subItem in item.children.slice(0,2)" :key="subItem.id">{{subItem.name}}</RouterLink>
<div class="layer">
<h4>分类推荐 <small>根据您的购买或浏览记录推荐</small></h4>
<ul>
<li v-for="goods in item.goods" :key="goods.id">
<RouterLink to="/">
<img :src="goods.picture" alt="">
<div class="info">
<p class="name ellipsis-2">{{goods.name}}</p>
<p class="desc ellipsis">{{goods.desc}}</p>
<p class="price"><i>¥</i>{{goods.price}}</p>
</div>
</RouterLink>
</li>
</ul>
</div>
</template>
</li>
</template>
</ul>
</div>
</template>
<script>
export default {
name: 'HomeCategory'
}
</script>
<style scoped lang='less'>
.home-category {
width: 250px;
height: 500px;
background: rgba(0, 0, 0, 0.8);
position: relative;
z-index: 99;
.menu {
li {
padding-left: 40px;
height: 55px;
line-height: 55px;
&:hover {
background: #27BA9B;
}
a {
margin-right: 4px;
color: #fff;
&:first-child {
font-size: 16px;
}
}
.layer {
width: 990px;
height: 500px;
background: rgba(255, 255, 255, 1);
position: absolute;
left: 250px;
top: 0;
display: none;
padding: 0 15px;
h4 {
font-size: 20px;
font-weight: normal;
line-height: 80px;
small {
font-size: 16px;
color: #666;
}
}
ul {
display: flex;
flex-wrap: wrap;
li {
width: 310px;
height: 120px;
margin-right: 15px;
margin-bottom: 15px;
border: 1px solid #eee;
border-radius: 4px;
background: #fff;
&:nth-child(3n) {
margin-right: 0;
}
a {
display: flex;
width: 100%;
height: 100%;
align-items: center;
padding: 10px;
&:hover {
background: #e3f9f4;
}
img {
width: 95px;
height: 95px;
}
.info {
padding-left: 10px;
line-height: 24px;
overflow: hidden;
.name {
font-size: 16px;
color: #666;
}
.desc {
color: #999;
}
.price {
font-size: 22px;
color: #CF4444;
i {
font-size: 16px;
}
}
}
}
}
}
}
&:hover {
.layer {
display: block;
}
}
}
}
}
.ellipsis {
white-space: nowrap;
text-overflow: ellipsis;
overflow: hidden;
}
.ellipsis-2 {
word-break: break-all;
text-overflow: ellipsis;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 2;
overflow: hidden;
}
</style>