一、组件介绍
-
每一个组件都是一个vue实例
-
每个组件均具有自身的模板template,根组件的模板就是挂载点
-
每个组件模板只能拥有一个根标签
-
子组件的数据具有作用域,以达到组件的复用
二、局部组件
<div id="app">
<local-tag></local-tag>
<local-tag></local-tag>
</div>
<script>
var localTag = {
data () {
return {
count: 0
}
},
template: '<button @click="btnAction">局部{{ count }}</button>',
methods: {
btnAction () {
this.count ++
}
}
}
new Vue({
el: "#app",
components: {
'local-tag': localTag
}
})
</script>
1 <!DOCTYPE html> 2 <html lang="zh"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>局部组件</title> 6 <script type="text/javascript" src="js/vue.js"></script> 7 </head> 8 <body> 9 <div id="app"> 10 <!-- 错的 --> 11 <!-- <localTag></localTag> --> 12 13 <!-- ① --> 14 <!-- <localtag></localtag> --> 15 16 <!-- ② ③ ④ ⑤ --> 17 <local-tag></local-tag> 18 <local-tag></local-tag> 19 20 <!-- 总结:组件与html公用的名称(组件名、方法名、变量名),不要出现大写,提倡使用-语法 --> 21 </div> 22 </body> 23 <script type="text/javascript"> 24 // 创建局部组件:就是一个拥有模板(满足vue写法)的对象 25 var localTag = { 26 // 模板 27 // 错误: 只能解析第一个标签,以它作为根标签 28 // template: '<div>局部组件1</div><div>局部组件2</div>' 29 template: '\ 30 <div>\ 31 <div>局部组件1</div>\ 32 <div>局部组件2</div>\ 33 </div>' 34 } 35 // 局部组件需要被使用它的父组件注册才能在父组件中使用 36 37 // 模板: html代码块 38 // 根组件,拥有模板,可以显式的方式来书写template,一般不提倡,模板就是挂载点及内部所有内容 39 // 注:挂载点内部一般不书写任何内容 40 new Vue({ 41 el: '#app', // old 42 // template: '<div></div>' // new 43 // 用components进行组件的注册 44 45 // ① 46 // components: { 47 // 'localtag': localTag 48 // } 49 50 // ② 51 // components: { 52 // 'local-tag': localTag 53 // } 54 55 // ③ 56 // components: { 57 // 'localTag': localTag 58 // } 59 60 // ④ 61 components: { 62 'LocalTag': localTag 63 } 64 65 // ⑤ 66 // ES6 key与value一直,可以单独写key 67 // components: { 68 // localTag 69 // } 70 }) 71 </script> 72 </html>
三、全局组件
<div id="app">
<global-tag></global-tag>
<global-tag></global-tag>
</div>
<script>
Vue.component('global-tag', {
data () {
return {
count: 0
}
},
template: '<button @click="btnAction">全局{{ count }}</button>',
methods: {
btnAction () {
this.count ++
}
}
})
new Vue({
el: "#app"
})
</script>
1 <!DOCTYPE html> 2 <html lang="zh"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>全局组件</title> 6 <script type="text/javascript" src="js/vue.js"></script> 7 </head> 8 <body> 9 <div id="app"> 10 <global-tag></global-tag> 11 <global-tag></global-tag> 12 </div> 13 </body> 14 <script type="text/javascript"> 15 // 创建全局组件: 组件名, {template:''} 16 Vue.component('global-tag', { 17 // data: function () { 18 // return { 19 // num: 0 20 // } 21 // }, 22 data () { 23 return { 24 num: 0 25 } 26 }, 27 template: '<button @click="btnClick">点击了{{num}}下</button>', 28 methods: { 29 btnClick () { 30 console.log("你丫点我了!!!"); 31 this.num ++ 32 } 33 } 34 }) 35 36 new Vue({ 37 el: '#app', 38 data: { 39 40 } 41 }) 42 </script> 43 </html>
四、父组件传递数据给子组件
-
通过绑定属性的方式进行数据传递
<div id="app">
<global-tag :sup_data1='sup_data1' :supData2='sup_data2'></global-tag>
</div>
<script type="text/javascript">
Vue.component('global-tag', {
props:['sup_data1', 'supdata2'],
template: '<div>{{ sup_data1 }} {{ supdata2 }}</div>'
})
new Vue({
el: '#app',
data: {
sup_data1: '数据1',
sup_data2: '数据2'
}
})
</script>
1 <!DOCTYPE html> 2 <html lang="zh"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>父传子</title> 6 <script type="text/javascript" src="js/vue.js"></script> 7 </head> 8 <body> 9 <div id="app"> 10 <!-- 通过属性绑定的方式 --> 11 <!-- <global-tag v-bind:abc='sup_d1' :supD2='sup_d2'></global-tag> --> 12 <global-tag v-bind:abc='sup_d1' :sup_d2='sup_d2'></global-tag> 13 <!-- 模板名用-连接命名,属性名用_连接命名 --> 14 </div> 15 </body> 16 <script type="text/javascript"> 17 // 子组件需要接受数据 18 Vue.component('global-tag', { 19 // 通过props来接收绑定数据的属性 20 // props: ['abc', 'supd2'], 21 props: ['abc', 'sup_d2'], 22 // template: '<div><p @click="fn">{{ abc }}</p></div>', 23 template: '<div><p @click="fn(abc)">{{ abc }}</p></div>', 24 methods: { 25 // fn () { 26 // alert(this.abc) 27 // } 28 fn (obj) { 29 console.log(obj, this.sup_d2) 30 } 31 } 32 }) 33 34 // 数据是父组件的 35 new Vue({ 36 el: '#app', 37 data: { 38 sup_d1: "普通字符串", 39 sup_d2: [1, 2, 3, 4, 5] 40 } 41 }) 42 </script> 43 </html>
五、子组件传递数据给父组件
-
通过发送事件请求的方式进行数据传递
<div id="app">
<global-tag @send_action='receiveAction'></global-tag>
</div>
<script type="text/javascript">
Vue.component('global-tag', {
data () {
return {
sub_data1: "数据1",
sub_data2: '数据2'
}
},
template: '<div @click="clickAction">发生</div>',
methods: {
clickAction () {
this.$emit('send_action', this.sub_data1, this.sub_data2)
}
}
})
new Vue({
el: '#app',
methods: {
receiveAction (v1, v2) {
console.log(v1, v2)
}
}
})
</script>
1 <!DOCTYPE html> 2 <html lang="zh"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>子传父</title> 6 <script type="text/javascript" src="js/vue.js"></script> 7 </head> 8 <body> 9 <div id="app"> 10 <!-- 通过发送事件请求的方式进行数据传递(数据作为请求事件的参数) --> 11 <global-tag @send_data='receiveData'></global-tag> 12 <p>{{ msg }}</p> 13 </div> 14 </body> 15 <script type="text/javascript"> 16 Vue.component('global-tag', { 17 data () { 18 return { 19 sub_v1: '普通字符串', 20 sub_v2: [1, 2, 3, 4, 5] 21 } 22 }, 23 template: '<button @click="btnClick">发送</button>', 24 methods: { 25 btnClick () { 26 console.log("子>>> ", this.sub_v1, this.sub_v2); 27 // 通过emit方法将数据已指定的事件发生出去 28 // 事件名, 参数... 29 this.$emit("send_data", this.sub_v1, this.sub_v2) 30 } 31 } 32 }) 33 34 // 数据是父组件的 35 new Vue({ 36 el: '#app', 37 data: { 38 msg: '' 39 }, 40 methods: { 41 receiveData(obj1, obj2) { 42 console.log("父>>> ", obj1, obj2) 43 this.msg = obj2; 44 } 45 } 46 }) 47 </script> 48 </html>
六、父子组件实现todoList
<div id="app">
<div>
<input type="text" v-model='value'>
<button @click='click'>提交</button>
</div>
<ul>
<item
v-for='(e, i) in list'
:key='i'
:ele='e'
:index='i'
@delete='deleteAction'
></item>
</ul>
</div>
<script type="text/javascript">
Vue.component('item', {
props: ['ele', 'index'],
template: '<li @click="item_click">{{ ele }}</li>',
methods: {
item_click: function () {
this.$emit('delete', this.index)
}
}
})
new Vue({
el: '#app',
data: {
value: '',
list: [],
},
methods: {
click: function () {
this.list.push(this.value)
this.value = ''
},
deleteAction: function (index) {
this.list.splice(index, 1)
}
}
})
</script>
1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="UTF-8"> 5 <title>组件todoList</title> 6 <script type="text/javascript" src="js/vue.js"></script> 7 </head> 8 <body> 9 <div id="app"> 10 <div> 11 <input type="text" v-model='in_val'> 12 <button @click='pushAction'>提交</button> 13 </div> 14 <!-- <ul> 15 <li @click='deleteAction(index)' v-for='(item,index) in list' :key="index">{{ item }}</li> 16 </ul> --> 17 18 <!-- 父 将list传输给 子 --> 19 <todo-list :list_data='list' @delete_action='deleteAction'></todo-list> 20 21 </div> 22 </body> 23 <script type="text/javascript"> 24 Vue.component('todo-list', { 25 props: ['list_data'], 26 template: '<ul><li v-for="(e, i) in list_data" :key="i" @click="li_action(i)">{{e}}</li></ul>', 27 methods: { 28 li_action (index) { 29 // 子 反馈index给 父 30 this.$emit('delete_action', index); 31 } 32 } 33 }) 34 35 36 new Vue({ 37 el: '#app', 38 data: { 39 in_val: '', 40 list: [] 41 }, 42 methods: { 43 pushAction () { 44 this.list.push(this.in_val); 45 this.in_val = '' 46 }, 47 deleteAction (index) { 48 this.list.splice(index, 1); 49 } 50 } 51 }) 52 </script> 53 </html>
七、搭建Vue开发环境
1、安装nodeJS
-
官网下载安装:https://nodejs.org/zh-cn/
2、安装脚手架
-
vue官网 => 学习 => 教程 => 安装 => 命令行工具(CLI)
安装全局vue:npm install -g @vue/cli
在指定目录创建vue项目:vue create my-project
进入项目目录启动项目:npm run serve
通过指定服务器路径访问项目页面:http://localhost:8080/
3、项目创建
babel:是一个 JavaScript 编译器。
eslint:是一个语法规则和代码风格的检查工具,可以用来保证写出语法正确、风格统一的代码。
4、vue基础模板
<template>
</template>
<script>
export default {
}
</script>
<style scoped>
</style>
npm install -g vue-cli
vue init webpack my-project
npm install -g cnpm --registry=https://registry.npm.taobao.org