目录
Vue.js 是一套构建用户界面的渐进式框架。与其他重量级框架不同的是,Vue 采用自底向上增量开发的设计。Vue 的核心库只关注视图层,它不仅易于上手,还便于与第三方库或既有项目整合。另一方面,当与单文件组件和 Vue 生态系统支持的库结合使用时,Vue 也完全能够为复杂的单页应用程序提供驱动。
Vue.js 提供了 MVVM (Model-View-ViewModel 的简写)数据绑定和一个可组合的组件系统,具有简单、灵活的 API。
MVVM: 它采用双向绑定(data-binding):View 的变动,自动反映在ViewModel,反之亦然。
Vue 框架有以下特点:
- 简洁: HTML 模板 + JSON 数据。
- 数据驱动: 自动追踪依赖的模板表达式和计算属性。
- 组件化: 用解耦、可复用的组件来构造界面。
- 轻量: ~24kb min+gzip,无依赖。
- 快速: 精确有效的异步批量 DOM 更新。
- 模块友好: 通过 NPM 或 Bower 安装,无缝融入你的工作流。
一.Vue模板语法
1.创建一个新的 Vue 实例 :
var app = new Vue({ });
2.准备 html(在 Vue 的 html 中使用{{}}来获取组件定义的 data 数据) :
<div id="sfsf">
{{message}}
</div>
3.引用Vue.js 搭建好 Vue 环境,开始准备使用 Vue :
<!-- 引入 vue -->
<script src="../vue.js"></script>
<script>
var app = new Vue({
//绑定 id 为 app 的 html 代码片段
el:'#app',
//定义在代码片段可以使用的数据
data:{
message:"hello"
}
});
</script>
一个 Vue 应用由一个通过 new Vue 创建的根 Vue 实例:
1).el(element)代表要绑定 html 代码片段的根元素;
2).data 定义该代码片段上绑定的数据
一.插值
数据绑定最常见的形式就是使用“Mustache”语法 (双大括号) 的文本插值:
<div id="sfsf">{{message}}</div>
Mustache 标签将会被替代为对应数据对象上 message 属性的值。无论何时,绑定的数据对象上 message 属性发生了改变,插值处的内容都会更新 .
二.JavaScript 表达式
在 Vue 模板中,提供了完全的 JavaScript 表达式支持
{{ number + 1 }}//数值运算
{{ ok ? 'YES' : 'NO' }}//三目运算符
{{ message.split('').reverse().join('') }}//字符串方法操作
注意:只能在模板中写入表达式,而不能使用 js 语句,所以下面的写法会报错:
<!-- 这是语句,不是表达式 -->
{{ var a = 1 }}
<!-- 流控制也不会生效,请使用三元表达式 -->
{{ if (ok) { return message } }}
二.指令
指令 (Directives) 是带有 v- 前缀的特殊属性。指令的职责是,当表达式的值改变时,将其产生的连带影响,响应式地作用于 DOM.
一.文本渲染
1. v-text: 在 html 中插入数据,跟{{ }}功能一致
<div id="sfsf">
<h3 v-text="msg"></h3>
<!-- 效果一致 -->
<h3>{{msg}}</h3>
</div>
<script>
new Vue({
el:'#app',
data:{
msg:'shanghai'
}
});
</script>
2. v-once: 数据只会更新一次,下次更新不影响dom
<div id="app">
<span v-once>{{msg}}</span>
<h3>{{msg}}</h3>
</div>
<script>
var app = new Vue({
el:'#app',
data:{
msg:'shanghai'
}
});
</script>
3. v-html: 可以显示html元素
<div id="app">
<span>{{msg}}</span>
<h3 v-html="msg"></h3>
</div>
<script>
var app = new Vue({
el:'#app',
data:{
msg:'<h1>Hello Vue!!!</h1>'
}
});
</script>
二.class和style绑定
1.v-bind指令可以绑定元素的属性,动态给属性赋值,比如:v-bind:class,v-bind:style,v-bind:href形式
格式: v-bind:属性名="组件中定义的数据"
简化为: 属性名="组建中定义的数据"
改写成: :class,:style,:href等
<div id="app">
<div title="你好">hello</div>
<hr />
<div v-bind:title="msg">fnoefhoijfi</div>
<hr />
<div :title="msg">fuhuef</div>
<hr />
<img :src="src" />
<hr />
<a :href="href">fsada</a>
</div>
<script type="text/javascript">
var app = new Vue({
el:"#app",
data:{
msg:"jisajfoif",
src:"https://www.baidu.com"
href:"http://www.sxt.com"
}
});
</script>
2. class: 绑定DOM对象的class样式有以下几种形式:
绑定多个class
使用对象classObject绑定
使用数组classlist绑定
绑定的对象可以同时切换多个class
<div id="app">
<div class="red green item">vue</div>
<hr />
<div :class="{red:true,green:false,item:true}">vue</div>
<hr />
<div :class="classObj">Vue</div>
<div :class="classList">Vue</div>
</div>
<script type="text/javascript">
var app = new Vue({
el:"#app",
data:{
classObj:{
red:true,
green:false,
item:true
},
classList:["red","green","test"]
}
});
</script>
对象和数组绑定的区别:
对象可以控制class的添加和删除,数组不能控制删除
3. style绑定
绑定形式与class一致
使用内联对象Object
直接传入对象styleobject
使用数组对象styleList
<div id="app">
<div style="color: red;font-size: 40px;">赢你大爷啊</div>
<hr />
<div :style="{'color':'red','font-size':'30px'}">赢你大爷啊</div>
<hr />
<div :style="styleObj">赢你大爷啊</div>
<hr />
<div :style="[styleObj,styleObj2]">赢你大爷啊</div>
</div>
<script type="text/javascript">
var ass = new Vue({
el:"#app",
data:{
styleObj:{
'color':'green',
'font-size':'15px',
'font-family':'隶书'
},
styleObj2:{
'background':'pink'
}
}
});
</script>
三.事件处理
1. 监听事件
语法:v-on:事件名
简写:@事件名监听事件 :
<button v-on:click="count++">增加</button>
<button @click="count--">减少</button>
2. 方法事件处理器
一般来说事件会绑定一个方法,在方法内部处理相关的事件逻辑。需要在 methods 属性中定义方法,然后 v-on 引用对应相关的方法名。
<div id="app">
count:{{count}}
<button @click="addCount()">增加</button>
<button @click="downCount()">减少</button>
</div>
<script type="text/javascript">
var sds = new Vue({
el:"#app",
data:{
count:0
},
methods:{
addCount:function(){
this.count++;
},
downCount:function(){
this.count--;
}
}
});
</script>
3. $event 对象
事件处理函数中访问 DOM 原生事件 event 对象,可以使用特殊变量$event 对象传入。
<div id="app">
<!-- 传入$event -->
<button v-on:click="greet($event)">greet</button>
</div>
<script>
var app = new Vue({
el:'#app',
data:{
greetText:'Hello Vue!'
},
//定义组件方法
methods:{
//使用 event 对象
greet: function (event) {
console.log(event.target.tagName);//BUTTON
}
}
});
</script>
4. 事件修饰符
Vue.js 为 v-on 提供了事件修饰符。通过由点 (.) 表示的指令后缀来调用修饰符。
- stop : 阻止 event 冒泡,等效于 event.stopPropagation()
- prevent : 阻止 event 默认事件,等效于 event.preventDefault()
- capture : 事件在捕获阶段触发
- self : 自身元素触发,而不是子元素触发
- once : 事件只触发一次
<div id="ass">
<div @click="father">
<div @click="child">child</div>
</div>
<hr />
<!--stop : 阻止event冒泡,等效于event.stopPropagation()-->
<div @click="father">
<div @click.stop="child">child</div>
</div>
<hr />
<!--prevent : 阻止event默认事件,等效于event.preventDefault()-->
<a href="http://www.baidu.com" @click.prevent="prevent1">百度</a>
<hr />
<!--capture : 事件在捕获阶段触发-->
<!--先触发父元素,再触发子元素-->
<div @click.capture="father">
<div @click="child">child</div>
</div>
<hr />
<!--self : 自身元素触发,而不是子元素触发-->
<div @click.self="father">father
<div @click="child">child</div>
</div>
<hr />
<!--once : 事件只触发一次-->
<div @click.once="child">child</div>
</div>
<script type="text/javascript">
var sfs = new Vue({
el:"#ass",
data:{
},
methods:{
father:function(){
console.log("父元素.........");
},
child:function(){
console.log("子元素............");
},
prevent1:function(){
console.log("23571234567890-");
}
}
});
</script>
5. 键值修饰符
在监听键盘事件时,我们经常需要监测常见的键值。Vue 允许为 v-on 在监听键盘事件时添加关键修饰符:
.enter, .tab , .delete (捕获“删除”和“退格”键), .esc , .space, .up, .down, .left, .right
<div id="dad">
<form action="http://www.baidu.com">
<input v-on:keyup.enter="submit">
<!--<input v-on:keyup.enter="submit"/>-->
<input v-on:keyup.13="enterKey" />
</form>
</div>
<script type="text/javascript">
var ggr = new Vue({
el:"#dad",
data:{
},
methods:{
enterKey:function(){
console.log("enterdasd.....");
}
}
});
</script>
四.条件渲染
1、v-if
当条件返回true时,执行
2、v-else
当if条件不满足时,执行(要结合v-if一起使用)
3、v-else-if
当满足条件时执行(要结合v-if一起使用)
4、v-show
满足条件时显示,不满足隐藏
5、v-if 和 v-show
两者的区别是v-if是“真正”的条件渲染,只有为true时才会被渲染。v-if也是“惰性”的,假如初始条件为false,那么条件变为true时才会发生第一次渲染。
v-show只是CSS的display属性的切换,不论初始条件是否成立,都会进行html渲染,然后改变display的值为none或者block。
一般来说v-if开销比较大,如果需要频繁切换显示不显示使用v-show,需要进行条件判断的但是改变很少的使用v-if。
<div id="app">
<div v-if="flag">你看不见我</div> {{flag}}
<hr />
<h3 v-if="age==18">狗蛋是18岁</h3>
<hr />
<h3 v-else>狗蛋不是18岁</h3>
<hr />
<h2 v-if="age>45">老司机</h2>
<hr />
<h2 v-else-if="age==18">刚成年</h2>
<hr />
<h2 v-else>小屁孩</h2>
<hr />
<h2 v-show="flag">谁还看不见谁啊</h2>
</div>
<script type="text/javascript">
new Vue({
el:"#app",
data:{
flag:true,
age:17
}
});
</script>
五. 列表渲染
1. v-for
可以把一组值进行列表渲染,语法形式: item in items,items 是源数据数组并且 item 是数组元素迭代的别名。
在 v-for 块中,对父作用域属性的完全访问权限。v-for 还支持一个可选的第二个参数为当前项的索引。
v-for 也可以遍历对象,可以指定三个形参:
形式: v-for="(value, key, index) in object"
value: 对象的值
key: 对象的键
index: 遍历的索引
<div id="ass">
<ul>
<li v-for="item in items">{{item.name}}</li>
</ul>
<hr />
<ul>
<li v-for="(item,index) in items">{{type}}--{{index}}--{{item.name}}</li>
</ul>
<hr />
<ul>
<li v-for="(key,index,value) in items">{{index}}--{{key}}--{{value}}</li>
</ul>
</div>
<script type="text/javascript">
new Vue({
el:"#ass",
data:{
type:"",
items:[
{name:'banana'},
{name:'apple'},
{name:'orange'}
]
}
});
</script>
2. key 属性
用 v-for 渲染列表时, 使用 key 属性给每个指定一个唯一的 ID 表示,那么可以在下次数据渲染时,提高渲染速度。它默认用“就地复用”策略。
如果数据项的顺序被改变,重复 ID 的元素将会被再次使用,不会重新渲染。这个默认的模式是高效的。需要用 v-bind 来绑定动态值
<div id="app">
<ul>
<li v-for="item in items" :key="item.id">{{item.name}}{{item.id}}</li>
</ul>
</div>
<script type="text/javascript">
new Vue({
el:"#app",
data:{
items:[
{id:1,name:'apple'},
{id:2,name:'pinapple'},
{id:3,name:'watermelon'}
]
}
});
</script>
3. 取值范围
v-for 也可以指定整数,用来重复多次使用模板。
<div id="app">
<ul>
<li v-for="i in 5">第 {{i}} 次</li>
</ul>
</div>
六.表单输入绑定
v-model
用 v-model 指令在表单控件元素上创建双向数据绑定。它会根据控件类型自动选取正确的方法来更新元素。
v-model 会忽略所有表单元素的 value、checked、selected 特性的初始值。因为它会选择 Vue 实例数据来作为具体的值。通过 JavaScript 在组件的 data 选项中声明初始值。
单个使用时v-model是逻辑值:true和false,多个一起使用需要指定value值,选中结果绑定v-model的数组。
<div id="root">
<!--文本框-->
<input type="text" v-model="txtMsg" placeholder="请输入用户名.." />
文本值:{{txtMsg}}
<hr />
<!--复选框-->
<input type="checkbox" v-model="ck" value="HTML5" /> 选中状态{{ck}}
<br />
<input type="checkbox" value="HTML5" v-model="lesson" /><label>HTML5</label>
<input type="checkbox" value="java" v-model="lesson" /><label>java</label>
<input type="checkbox" value="Vue" v-model="lesson"/><label>Vue</label>
<p>多选结果:{{lesson}}</p>
<!--单选框-->
<input type="radio" value="yes" v-model="love"/><label for="">喜欢</label>
<input type="radio" value="no" v-model="love"/><label for="">不喜欢</label>
<input type="radio" value="all" v-model="love"/><label for="">都喜欢</label>
<p>结果:{{love}}</p>
<!--下拉框-->
<select name="" id="" v-model="selected">
<option value="watermelon">watermelon</option>
<option value="banana">banana</option>
<option value="apple">apple</option>
</select>
<h3>结果:{{selected}}</h3>
</div>
<script type="text/javascript">
var efd=new Vue({
el:"#root",
data:{
txtMsg:"",
ck:"",
lesson:[],
love:"",
selected:""
}
});
</script>
下拉框绑定
div id="dada">
<select name="" id="" v-model="selected">
<option :value="item.value" v-for="item in list">{{item.text}}</option>
</select>
</div>
<script type="text/javascript">
new Vue({
el:"#dada",
data:{
list:[
{text:'watermelon',value:'1'},
{text:'apple',value:'2'},
{text:'banana',value:'3'}
]
}
});
</script>
修饰符
使用v-model绑定数据后,可以使用修饰进行数据处理:
lazy:绑定数据默认实时更新,lazy可以在onChange触发
number:返回数字类型的值,转换不成返回NaN
trim:去除数据的前后空格
<div id="dada">
<p><input type="text" v-model.lazy="name"/>{{name}}</p>
<p><input type="text" v-model.number="age" /></p>
<p><input type="text" v-model.trim="cont" /></p>
<p><button @click="show()">显示值</button></p>
</div>
<script type="text/javascript">
new Vue({
el:"#dada",
data:{
name:"",
age:"",
cont:""
},
methods:{
show:function(){
console.log(this.name);
console.log(this.age);
console.log(this.cont);
console.log(typeof this.age);
}
}
});
</script>
三.组件
组件 (Component) 是 Vue.js 最强大的功能之一。组件可以扩展 HTML 元素,封装可重用的代码。
一.定义组件
Vue 自定义组件分为两种:全局注册和局部注册,全局组件可以在任何地方引用,局部组件只能在当前 Vue 实例使用。
1. 全局注册: 使用 Vue.component(tagName, options)来定义
/*定义全局组件*/
Vue.component('my-component',{
template:'<h4>我是自定义组件</h4>'
});
注意,HTML 特性是不区分大小写的,所有在定义组件时尽量使用中划线“-”来指定组件名。即使,使用了驼峰标示命名如:myComponent,在页面引用时仍然要使用<my-component>进行引用。
2. 局部注册: 在 Vue 实例中使用 components 属性来定义
var app = new Vue({
el:'#app',
//使用 components 关键字
components:{
'inner-component':{
template:'<h4>我是局部注册组件</h4>'
}
}
});
二.使用组件
<div id="app">
<!-- 使用组件 -->
<my-component></my-component>
<inner-component></inner-component>
</div>
<script>
/*定义全局组件*/
Vue.component('my-component',{
template:'<h4>我是自定义组件</h4>'
});
/***
* 此种定义方式全局注册,在任何地方都可以通过自定义标签名进行引用
* */
var app = new Vue({
el:'#app',
//使用 components 关键字
components:{
'inner-component':{
template:'<h4>我是局部注册组件</h4>'
}
}
});
</script>
三.is属性
is属性
在table标签中直接使用自定义组件,无法正常显示。DOM解析时会解析到<table>标签的外部:
原因是:table/ol/ul/select 这种html标签有特殊的结构要求,不能直接使用自定义标签。他们有自己的默认嵌套规则,比如:
table> tr> [th, td];
ol/ul > li;
select > option
<table id="mckc">
<tr is="my-hello">
</tr>
</table>
<script type="text/javascript">
Vue.component("my-hello",{
template:"<h3>hello stranger</h3>"
});
new Vue({
el:"#mckc"
});
</script>
四.模版
当模板的html结构比较复杂时,直接在template属性中定义就不现实了,效率也会很低,此时我们可以使用模板,定义模板的四种形式:
1)直接使用字符串定义
2)使用<script type="text/x-template">
3)使用<template>标签
4)使用.vue组件,需要使用模块加载机制
在使用直接字符串模板时、x-template和.vue组件时,不需要is进行转义。
<div id="app">
<my-hello1></my-hello1>
<my-hello2></my-hello2>
<my-hello3></my-hello3>
<my-hello4></my-hello4>
</div>
<script type="text/x-template" id="tpl3">
<ul>
<li>01</li>
<li>02</li>
<ul>
</script>
<template id="tpl4">
<ul>
<li>012</li>
<li>023</li>
<ul>
</template>
<script type="text/javascript">
//1.直接使用字符串定义
var tpl = "<div><button>按钮</button><span>hello</span></div>";
var tpl2=`
<div>
<button>按钮2</button>
<span>hello22</span>
</div>
`;
console.log(tpl2);
//定义组件
Vue.component("my-hello1",{
template:tpl
});
Vue.component("my-hello2",{
template:tpl2
});
Vue.component("my-hello3",{
template:"#tpl3"
});
Vue.component("my-hello4",{
template:"#tpl4"
});
new Vue({
el:"#app"
});
</script>