1、需求背景
在uni-app开发微信小程序的需求中,需要全局实现以下两个组件:
弹窗提示: 在小程序的任意页面,只要状态满足,需要弹出XXX提醒窗口。
置顶按钮: 在小程序的大部分页面,只要状态满足,需要显示置顶按钮并可返回顶部。
实现方案1:
以传统的vue组件开发方式,需要安装(或在components目录下编写自己的组件)、引用、注册,三个步骤后才能使用组件,如下:
import XXX from "@/components/XXX"
export default {
components: {
XXX
}
}
结论: 该方案不适合全局组件注册场景,是当小程序页面很多的时候,每个页面都需要引用、注册等步骤,会造成大量的冗余代码。
实现方案2:
传统vue组件,需要安装、引用、注册,三个步骤后才能使用组件,easycom将传统vue组件的使用简化为一步。 只要组件安装在项目根目录或uni_modules的components目录下,并符合components/组件名称/组件名称.vue或uni_modules/插件ID/components/组件名称/组件名称.vue目录结构。就可以不用引用、注册,直接在页面中使用。 如下:
<template>
<view class="container">
<uni-list>
<uni-list-item title="第一行"></uni-list-item>
<uni-list-item title="第二行"></uni-list-item>
</uni-list>
</view>
</template>
<script>
// 这里不用import引入,也不需要在components内注册uni-list组件。template里就可以直接用
export default {
data() {
return {}
}
}
</script>
自定义easycom配置的示例
"easycom": {
"autoscan": true,
"custom": {
"^uni-(.\*)": "@/components/uni-$1.vue", // 匹配components目录内的vue文件
"^vue-file-(.*)": "packageName/path/to/vue-file-$1.vue" // 匹配node_modules内的vue文件
}
}
官网文档:点击跳转
结论: 该方案虽然不需要去引用、注册,但是仍然需要每个页面引入。
实现方案3(最终)
使用vue-inset-loader,在指定位置插入自定义内容(全局的组件),具体方式如下:
// 第一步
npm install vue-inset-loader --save--dev
// 第二步 在vue.config.js(HBuilderX的项目没有,新建一个)中注入loader
const path = require('path')
module.exports = {
configureWebpack: {
module: {
rules: [{
test: /\.vue$/,
use: {
loader: path.resolve(__dirname,"./node_modules/vue-inset-loader")
},
}]
},
}
}
// 第三步 pages.json配置文件中添加insetLoader
"insetLoader": {
"config": {
"onlineLabel": "<OnlineTips ref='onlineTips'></OnlineTips>",
"scrollLabel": "<ScrollTop ref='scrollTop'></ScrollTop>",
},
// 全局配置
"label": ["onlineLabel", "scrollLabel"],
"rootEle": "view",
}
在components目录下,编写 OnlineTips、ScrollTop两个自己开发的组件。
组件的显示:用v-if做判断,条件成立则显示我们的组件内容。
结论: 通过方案三,我们实现了微信小程序组件的全局引入。
置顶按钮实现逻辑
scrollTop组件:
<template>
<view class="scrollTop-main" v-if="isShow">
<view class="txt" @click="goTop()">回到顶部</view>
</view>
</template>
<script>
export default {
name: "scrollTop",
data() {
return {
isShow: false
}
},
methods: {
goTop() {
uni.pageScrollTo({
scrollTop: 0,
duration: 300
});
}
}
}
</script>
<style lang="scss" scoped>
.scrollTop-main {
position: fixed;
width: 110rpx;
height: 110rpx;
right: 40rpx;
bottom: 130rpx;
z-index: 99;
color: #fff;
text-align: center;
font-size: 28rpx;
border-radius: 100%;
line-height: 40rpx;
display: flex;
align-items: center;
font-weight: bold;
background: linear-gradient(90.33deg, #6F8AF7 0.19%, #696DE9 99.72%);
box-shadow: 0px 1px 10px rgba(0, 0, 0, 0.25), 0px 0px 5px #96B3FF;
.txt {
padding: 0 20rpx;
}
}
</style>
任意页面调用方式,滚动距离大于screenHeight就显示:
onPageScroll(e) {
if (e.scrollTop > wx.getSystemInfoSync().screenHeight) {
this.$refs.scrollTop.isShow = true;
} else {
this.$refs.scrollTop.isShow = false;
}
}