1.安装vue并创建一个vue3项目
vue create test-components
安装完的目录结构
我们做如下调整:
我们将src重命名为examples, 并添加packages目录,用来存放我们的自定义组件. 但是cli默认会启动src下的服务,如果目录名变了,我们需要手动修改配置,vue-cli3中提供自定义打包配置项目的文件,我们只需要手动创建vue.config.js即可.我们具体修改如下:
const { defineConfig } = require("@vue/cli-service");
const path = require("path");
function resolve(dir) {
return path.join(__dirname, dir);
}
module.exports = defineConfig({
transpileDependencies: true,
pages: {
index: {
entry: "examples/main.ts", // 改入口
template: "public/index.html",
filename: "index.html",
},
},
chainWebpack: (config) => {
config.resolve.alias.set("@", resolve("./examples")); //@ 别名
config.module
.rule("js")
.include.add(resolve("./packages"))
.end()
.use("babel")
.loader("babel-loader")
.tap((options) => {
return options;
});
},
});
2.开始写组件
1、vue组件 ,在 packages 文件里建一个 c-button文件,结构如下 ,src/c-button.vue 和 index.ts
c-button.vue
<template>
<button class="test-components">
<slot></slot>
</button>
</template>
<script>
import { defineComponent } from "vue";
export default defineComponent({
name: "c-buttom",
props: {
msg: String,
},
});
</script>
<style>
.test-components {
width: 200px;
height: 200px;
background-color: #ff8500;
padding: 10px;
border-radius: 10px;
box-sizing: border-box;
}
</style>
index.ts
import testComponents from "./src/c-buttom.vue";
// 为组件提供 install 安装方法,供按需引入
testComponents.install = function (Vue:any) {
Vue.component(testComponents.name, testComponents);
};
// 默认导出组件
export default testComponents;
2、写一些公用方法 c-common,里面直接建一个 index.ts 文件即可
const common: any = {
...
}
export default common;
3.在packages文件建一个index.ts 把组件导出集中在这
import CButton from "./c-button/index"; //引入
import Common from './c-common/index'; //引入
const components = [CButton];
// 定义 install 方法,接收 Vue 作为参数。如果使用 use 注册插件,则所有的组件都将被注册
const install: any = function (Vue: any) {
// 判断是否安装
if (install.installed) return;
// 遍历注册全局组件
components.map((component) => Vue.component(component.name, component));
};
// 判断是否是直接引入文件
const win: any = window;
if (typeof win !== "undefined" && win.Vue) {
install(win.Vue);
}
export default {
// 导出的对象必须具有 install,才能被 Vue.use() 方法安装
install,
// 以下是具体的组件列表
CButton,
Common
};
3.测试组件代码
在main.ts 里全局引入
import { createApp } from "vue";
import App from "./App.vue";
import router from "./router";
import store from "./store";
import myComponents from "../packages/index"; // 引入
const app = createApp(App);
app.config.globalProperties.$common = myComponents.Common; // 把方法挂载到 this
app.use(store).use(myComponents).use(router).mount("#app");
直接使用 this.$common 会报错,在main.ts 根目录建一个 test.d.ts 文件,定义 $common的类型
import { ComponentCustomProperties } from "@vue/runtime-core";
declare module "@vue/runtime-core" {
interface ComponentCustomProperties {
$common: object; // 这里填类型
}
}
// 必须导出,才能在其他文件中使用
export default ComponentCustomProperties;
调用的时候需要在页面中引用
import {
getCurrentInstance,
} from "vue";
let { proxy } = getCurrentInstance();
proxy.$common.xx();
4.组件使用
<template>
<div class="home">
<img alt="Vue logo" src="../assets/logo.png" />
<c-buttom>sdasd</c-buttom>
</div>
</template>
<script lang="ts">
import { defineComponent } from "vue";
export default defineComponent({
name: "HomeView",
components: {},
mounted() {
console.log(this.$common);
},
});
</script>