webpack构建vue单文件组件
1.安装vue-loader和vue-template-compiler
npm i vue-loader vue-template-compiler --save-dev
2.配置webpack.config.js
var path = require('path'); var webpack = require('webpack'); var VueLoaderPlugin = require('vue-loader/lib/plugin'); module.exports = { entry: './src/main.js', // 项目的入口文件,webpack会从main.js开始,把所有依赖的js都加载打包 output: { filename: 'build.js' // 打包后的文件名 }, plugins:[ new VueLoaderPlugin(), ], devServer: { contentBase:path.resolve(__dirname,"dist"), historyApiFallback: true, overlay: true }, resolve: { alias: { 'vue$': 'vue/dist/vue.esm.js' } }, module: { rules: [ { test: /\.css$/, use: [ 'vue-style-loader', 'css-loader', ] }, { test: /\.(png|jpg|gif|svg)$/, loader: 'file-loader', options: { name: 'img/[name].[ext]?[hash]' } }, { test: /\.vue$/, loader: 'vue-loader', } ] } };
在src目录下新建一个App.vue
.vue文件分成3个部分
template:html代码,相对于用extend定义组件时的template部分
script:js代码,用extend定义组件时的methods、data这些部分都写在这里
style:css
<template> <div id="app"> <h1>{{ msg }}</h1> <img src="./img/icon_bindap.png"> <input type="text" v-model="msg"> </div> </template> <script> var util = require("./util"); export default { name: 'app', data () { return { msg: 'Welcome to Your Vue.js' } }, created() { this.fetchData(); }, methods: { fetchData() { var test = util.testfunc(); this.msg = test; } } } </script> <style lang="css"> h1 { color: green; } </style>
vue文件里template的根div的id可以不要,js里的name也可以不要,name和id也不要求一样
util.js
exports.testfunc = function test(){ console.log('test'); return "test"; }
main.js
相当于在vue里嵌入一个子组件
components声明子组件,template使用子组件
new vue对象,el:"app",相对于把一个叫vue的组件自动挂载到index.html的app元素下,里面有一个子组件app,类似 vue组件 中的:
new todoItem().$mount('#todoItem');
import Vue from 'vue'; import App from './App.vue'; import './style/common.css'; new Vue({ el: '#app', template: '<App/>', components: { App } })
index.html
挂载vue到div#app
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <div id="app"></div> <script src="build.js"></script> </body> </html>
碰到的问题:
1.ExtractTextPlugin配置了css路径后,css不起作用的问题:
index.html中没有用link引入css,可以手动修改index.html,引入css
也可以结合HtmlWebpackPlugin,HtmlWebpackPlugin会自动加入link引入需要的css文件,也会自动加入script引入需要的js文
件
2.HtmlWebpackPlugin没有配置模板时,会使用默认模板生成index.html,自动加入需要的css和js的引用,如果目标文件夹下也有index.html,会被覆盖
3.build时出现错误:webpack vue-loader was used without the corresponding plugin. Make sure to include VueLoaderPlugin
新版本的vue-loader需要配合一个 webpack 插件才能正确使用:
// webpack.config.js
const VueLoaderPlugin = require('vue-loader/lib/plugin')
module.exports = {
// ...
plugins: [
new VueLoaderPlugin()
]
}
4.Vue packages version mismatch 错误:
vue-template-compiler和vue版本必须一致,如果不一致,重新安装 vue-template-compiler让其跟vue版本一致即可
5.文件名不区分大小写,上例中App.vue在main.js中引入时,可以写成:
import App from './app.vue';
6.如果App.vue引入后的名字改成其他,则后面模板的定义要改成对应的名字,比如:
import Vue from 'vue';
import App2 from './app.vue';
import './style/common.css';
new Vue({
el: '#app',
template: '<App2/>',
components: { App2 }
})
标红三者要保持统一