组件

202002060849

组件化

利用组件化开发,拆分功能,封装组件,单独维护

组件注册

// 定义一个名为 button-counter 的全局组件Vue.component('button-counter', {    data: function () {        // data必须是一个函数,如果data是一个对象的话,那么所有button-counter都会共享同一份数据        return { count: 0 }    },    template: '<button v-on:click="count++">You clicked me {{ count }} times.</button>'});new Vue({ el: '#app' });
<!-- 使用自定义组件,必须使用短横线的方式使用组件 --><button-counter></button-counter>
new Vue({     el: '#app' ,     components:{         'compomenta':{             template:`                <div>componenta</div>             `         }     }});

组件通信

const introduce = {    template:'<h1 @click="fun()">{{msg}}</h1>',    methods: {        fun() {            // 触发上一层事件,第一个参数是事件名称,第二个参数是传递给父组件的参数           this.$emit('delete',"delete it");        }    },    props:['msg'] // 子组件需要声明要接收的参数}new Vue({    el: '#app',    data:{ msg:'大家好,我是渣渣辉' },    methods: {        handleDelete(args) { console.log(args); }    },    components:{ introduce }});
<div id="app">    <!-- 父组件向子组件传递msg -->    <!-- 父组件监听子组件的delete事件 -->    <introduce :msg="msg" @delete="handleDelete"></introduce></div>

使用一个事件中心,这个事件中心可以监听事件、触发事件

var hub = new Vue();// 注册事件hub.$on('event', (val) => {    this.num += val;});// 触发事件hub.$emit('event', 2);// 销毁事件hub.$off('event');

组件参数校验

//...props: {    // 要求传递过来的msg必须是String类型    msg: String,    id: [Number,String], // 可以是数字或者字符串类型    content: {        type: String,        required: false, // 非必传        defaultValue: 'cxk', // required必须为false这个值才会生效        validator: function(val) {            // 自定义校验器            retrun val.length === 3;        }    }}

非props特性

插槽

<child>    <!-- 给插槽起名 -->    <div slot='header'>header</div>    <div slot='footer'>footer</div>    <!-- 下面这个没有名字,所以会匹配到第一个slot(没有名字) -->    <div>no name</div></child>
'child':{    template: `    <div>      <slot></slot>      <slot name="header">default value</slot>       <slot name="footer"></slot>    </div>    `}

动态组件

<component v-bind:is="currentTabComponent"></component>

组件事件

当定义子组件时,默认的原生事件监听@xxx不会生效,可以加上.native修饰符

组件使用中的细节

组件化带来的问题

vue-router

import Info from '../views/Info.vue';
const routes = [  //...  {    path: '/info',    name: 'info',    component: Info,  },];

单文件组件

<template>    <!-- 组件代码区域 --></template><script>// js代码区域export default {  ...}</script><style scoped>    /* 样式代码区域 */</style>
npm install vue-loader vue-template-compiler vue -D
const VueLoaderPlugin = require("vue-loader/lib/plugin");const vuePlugin = new VueLoaderPlugin();module.exports = {    ....    plugins:[        ...        new vueLoader()    ],    module : {        rules:[            ...            {                 test:/\.vue$/,                loader:"vue-loader"            }        ]    }}
import Vue from 'vue';import App from './App.vue';const vm = new Vue({    el:'#app',    render:h=>h(App)})