小白进阶: 教你撸一个简单的Vue自定义动态组件(一)
components下创建 toast 文件夹, 文件夹里面创建 toast.vue 和 index.js
toast.vue: <template> <div id="toastWrap" :class="[className,showAnimation ?'fadein':'fadeout',appointId==''?'fixed':'absolute']" v-if="show"> <span :class="['iconfont',type]"></span> {{text}} </div> </template> <script> export default { name: '', data(){ return {} }, components: {}, created(){}, mounted(){}, methods: {} } </script> <style scoped> .fixed{ position: fixed; } .absolute{ position: absolute;; } #toastWrap{ left: 50%; top:50%; background: rgba(0, 0, 0, 0.7); padding: 10px; border-radius: 5px; transform: translate(-50%,-50%); color:#fff; } .fadein { animation: animate_in 0.25s; } .fadeout { animation: animate_out 0.25s; opacity: 0; } @keyframes animate_in { 0% { opacity: 0; } 100%{ opacity: 1; } } @keyframes animate_out { 0% { opacity: 1; } 100%{ opacity: 0; } } </style>
index.js: import vue from 'vue' import toastComponent from './toast.vue' const ToastConstructor = vue.extend(toastComponent) console.log("初始化一个vue构造器") console.log(ToastConstructor) function showToast(obj) { // 实例化一个 toast.vue let param = { text: obj.text || '', // className 自定义class className: obj.className || '', type: obj.type || 'icon-tishi1', // appointId 父元素class 用于定位 appointId: obj.appointId || '', duration: obj.duration || 3000 } console.log("传参情况") console.log(param) const toastDom = new ToastConstructor({ el: document.createElement('div'), data() { return { text: param.text, show: true, className: param.className, type: param.type, showAnimation: true, appointId: param.appointId } } }) //挂载到文档 if (param.appointId !== '') { console.log("appointId不等于空") console.log(param.appointId) document.getElementById(param.appointId).appendChild(toastDom.$el) } else { console.log("appointId等于空") document.body.appendChild(toastDom.$el) } setTimeout(() => { toastDom.showAnimation = false }, param.duration - 1250) setTimeout(() => { toastDom.show = false }, param.duration) } function registryToast() { // 将组件注册到 vue 的 原型链里去, // 这样就可以在所有 vue 的实例里面使用 this.$toast() vue.prototype.$toast = showToast } export default registryToast
main.js: import toastComponent from '../src/components/toast' Vue.use(toastComponent)
在需要使用的地方调用
that.$toast({text:'填写用户名/手机号/邮箱',className:"loginTip",appointId:'loginFrom',duration:3500})
我的理解:先写一个模板,然后通过vue.extend初始化为一个vue构造器,然后通过一个函数去实例化 挂载在Vue原型链和文档中,通过vue调用显示隐藏。欢迎讨论其他写法,和各种写法的优点缺点
搜索关键词:
vue 自定义组件动态加载/vue 自定义组件封装
参考资料:
从零开始徒手撸一个vue的toast弹窗组件
https://blog.csdn.net/weixin_33831673/article/details/87961145
添加自定义vue全局方法,同时给自定义的方法 传递component调用其方法
https://blog.csdn.net/ling369523246/article/details/78450418