本文目录
- 1.封装mheader组件
- 2.背景图片模糊
- 3.组件绑定数据的优化处理
- 4.better-scroll优化滚动
- 5.格式化歌曲数据
- 6.使用mixin快速开发
- 7.请求接口优化
- 8.添加转场动画
1.封装mheader组件
header在很多地方可以用到,但是在一些地方的背景色不同,所以封装的时候可以动态的传递一个背景色数据
首先需要新建一个组件文件,注意header已经是标签名了,所以不能做再命名为header,这里命名为mheader
<template>
<div class="mheader" :class="{'red':red}">
<i class="iconfont icon-zuo" @click="goBack"></i>
<slot></slot>
</div>
</template>
<script>
export default {
name: "mheader",
data() {
return {};
},
props: {
red: {
type: Boolean,
default: true
}
},
methods: {
goBack() {
this.$router.go(-1);
}
}
};
变量red默认为true,当变量red为true时,把类名red赋予组件。这样的话,在组件使用的时候,如果不传递red值,则默认为有类名red所赋予的背景色,如果red传递值为false,则不会有模拟的背景色。
我们在引用mheader组件的时候,在组件标签内添加的代码可以自动渲染到<slot>中。
2.背景图片模糊
思路:通过伪类的方式,为盒子本来的背景图片上再添加一层图片,进行模糊处理。
div{
background-image: url("./bg.png");
&:after{
content: '';
width: 100%;
height: 100%;
left: 0;
top: 0;
background: inherit;
filter:blur(20px);
}
}
只所以用伪类的方式再添加一层,而不在原本的背景上进行模糊,是因为fiter进行模糊的范围并不完全和原本的背景贴合,所以通过伪类,我们可以很方便的对模糊的位置进行调整。经过优化调整,less代码如下:
div{
background-image: url("./bg.png");
&:after{
content: '';
width: calc(100% + 80px);
height: calc(100% + 80px);
left: -40px;
top: -40px;
background: inherit;
filter:blur(20px);
}
}
这个时候模糊处理后的伪类背景会超过原本的盒子范围,我们可以在恰当的地方添加上overflow: hidden;
3.组件绑定数据的优化处理
如下情况:
<top :title="newSongsData[0].name"
:img="newSongsData[0].picurl"
:count="formatData.length"></top>
浏览器会报一些警示错误,原因是axios发起的请求是异步的,当页面最初渲染的时候数据并没有拿到,所以要传递的三个数据也就不存在。解决方法之一是用v-if
<top v-if="newSongsData.length"
:title="newSongsData[0].name"
:img="newSongsData[0].picurl"
:count="formatData.length"></top>
这样做的缺点是一些情况下就算请求完成了newSongsData也是没有数据的,长度自然始终为0。所以我们可以通过computed计算属性进行优化
<top :title="title" :img="img"
:count="formatData.length"></top>
computed: {
title() {
if (this.formatData.length > 0) {
return this.formatData[0].name;
} else {
return "暂无数据";
}
},
img() {
if (this.formatData.length > 0) {
return this.formatData[0].al.picUrl;
} else {
return "";
}
}
},
这样处理还有一个好处就是当数据真的不存在的时候变量也会有默认值,增加了用户体验。
4.better-scroll优化滚动
better-scroll不依赖任何框架,滚动的最外层盒子.wrapper,作用于其中的第一个元素,但是又不影响盒子内的其它元素。但是实际开发中我们给想要滚动的盒子内只添加一个子元素,以便更好的实现滚动。
.wrapper的高度一定要是固定的。
安装:npm install better-scroll --save
因为这个插件我们会在项目的很多个地方都用到,同时还会有一些方法:比如实例化方法和数据改变之后重新刷新的方法,为了避免这些引用和方法多次的书写,我们可以把这个插件再做进一步的封装。
首先封装一个scroll组件scroll.vue
详细代码“Vue插件”文集中有详细讲解。
在想使用scroll插件的页面中,首先需要引用
import scroll from "@/components/scroll";
html结构
<scroll class="page-info-list" :data="formatData">
<songlist :data="formatData" @clickItem="addToPlay"></songlist>
</scroll>
scroll的page-info-list是赋值高度的样式。
.page-info-list {
height: calc(100vh - 380px);
overflow: hidden;
}
这样的,scroll就可以正常起作用了。
5.格式化歌曲数据
在多个地方请求获得的歌曲数据,数据格式并不一样,这样的话我们用同一个组件去渲染,会发生数据渲染错误的现象,虽然这在正常的工作开发很少遇到,但是多一点准备总是必要的。
我们可以自己封装一个工具,专门用来格式化指定的数据
首先在src文件夹中新建一个common文件夹,然后新建一个js文件夹,js文件夹中新建一个util.js文件
export function formatSongDetail(val){
const newVal = []
val.forEach((item) =>{
const detail = {}
detail.id = item.id
detail.al = Object.assign({}, item.al || item.album || item.song.album)
detail.ar = [].concat(item.ar || item.artists || item.song.artists)
detail.name = item.name
newVal.push(detail)
})
return newVal
}
在需要使用到这个工具的页面中直接引入这个工具
import { formatSongDetail } from "../../common/js/util";
然后就可以直接使用formatSongDetail 方法了
6.使用mixin快速开发
组件的作用是可以实现复用,但是组件的使用都是全部使用,但是有些情况,我们会用到这个组件的一部分和另外一个组件的一部分,这时候应该怎么办呢?解决方法就是vue提供的mixins属性
这个需要多次复用的代码我们可以看做是一个工具,在common文件夹下的js文件夹下新建一个infoMixin.js文件,把打算多次复用的代码写入
import top from "@/components/top.vue";
import songlist from "@/components/songlist.vue";
import scroll from "@/components/scroll.vue";
export default{
components: {
top,
songlist,
scroll
},
data() {
return {
formatData:[]
};
},
computed: {
title() {
if (this.formatData.length > 0) {
return this.formatData[0].name;
} else {
return "暂无数据";
}
},
img() {
if (this.formatData.length > 0) {
return this.formatData[0].al.picUrl;
} else {
return "";
}
}
},
}
然后在使用这些代码的页面中进行引用
import infoMixin from '../../common/js/infoMixin'
添加minxins属性进行挂载使用
mixins:[infoMixin]
7.请求接口优化
当进入首页的时候,会发起关于首页的请求,然后进入到排行榜,会发起关于排行榜的请求,然后进入到歌曲详情,会发起关于歌曲详情的请求,这时候,我们点击后退,当后退到指定页面时,关于该页面的请求又会重新发送一遍,这样会增大服务器的压力,实际操作中用户频繁的前进和后退的时间间隔非常的短,数据并不会有什么变化,其实并不用重新更新页面。
产生这种情况的原因是因为把所有的路由都规划成了平级的关系,然进入到某个页面的时候,router.js会销毁路由,然后重新建立路由,所以每次前进和后退,都是一次路由的销毁与重新建立。
解决方法是将整个项目的路由规划成合理的父子路由关系,这样的话router就会很好的分辨出各个页面的层级关系,从而让进入子路由页面的时候,router并不会完全销毁父路由。
vue还提供了另外一种解决方案,就是keep-alive
比如把App.vue写成下面这样的
<template>
<div id="app">
<keep-alive>
<router-view/>
<keep-alive>
</div>
</template>
这样我们在进入项目的所有页面,然后后退,的确页面都不会重新请求和渲染,但是这时候发现在重新进入页面的时候,所有进入过的页面都变成静态的了,甚至连一些需要动态传参的页面也变成首次进入的那张静态页面了,这并不符合开发需求,所以这种方式只适合于固定的页面渲染,而不适合动态的页面渲染。
所以我们选用的是改造路由的方式,也就是改造router.js文件
export default new Router({
routes: [
{
path: '/',
name: 'home',
component: Home,
children: [
{
path: '/recommend',
name: 'recommend',
component: recommend,
},
{
path: '/rank',
name: 'rank',
component: rank,
children: [
{
path: ':id',
name: 'rankinfo',
component: rankinfo,
}
]
},
]
}
]
});
改造完之后所有的页面都属于‘/’的子路由了,所以我们在home页面还需要改造一下,也就是在本来home的页面元素之下放一个<router-view></router-view>
,当路由识别到我们要进入子页面的时候,会把子页面渲染到这个<router-view></router-view>
中,同理,所有存在父子关系的页面,都应该在父页面放一个<router-view></router-view>
以便路由进行识别和渲染。
这个时候我们发现进入子页面的时候,子页面是渲染在父页面的下方的,这是因为我们放置router-view的时候也是放置在父页面的最下方,解决方法是我们给子页面的div增加一个page样式,用来覆盖在父页面的上方
.page {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background-color: #f3f4f9;
z-index: 9999;
overflow: scroll;
}
8.添加转场动画
给打算做转场动画的所有router-view都包裹在transition标签中
<transition name="slide">
<router-view></router-view>
</transition>
然后添加公共样式
.slide-enter-active,.slide-leave-active{
transition: all .3s;
}
.slide-enter,.slide-leave-to{
transform: translate3d(100%,0,0)
}
网友评论