什么是 Vue?
考虑这个需求: 我们要把一个 json对象的数据,显示到一个元素上去。
如果我们使用之前的JS,那么就需要先用getElement获取元素,然后在innerHTML显示数据
但是如果使用Vue的话,就只需要提供数据,然后把数据绑定到元素的id就可以啦!
比如这样一个把数据显示到div的例子:
<script src="C:/Users/msi-/Desktop/work/vue.min.js"></script>
<div id="div1">
{{gareen.name}}
</div>
<script>
//准备数据
var gareen = {"name":"盖伦","hp":616};
//通过vue.js 把数据和对应的视图关联起来
new Vue({
el: '#div1',
data: {
message: gareen
}
})
</script>
监听事件
比如写一个点击事件 v-on:
<script src="https://how2j.cn/study/vue.min.js"></script>
<div id="div1">
<div>一共点击了 {{clickNumber}}次</div>
<button v-on:click="count">点击</button>
</div>
<script>
new Vue({
el: '#div1',
data: {
clickNumber:0
},
methods:{
count: function(){
this.clickNumber++;
}
}
})
</script>
其中的v-on还可以用@代替,比如写成@click="count"
v-if
v-if条件判断 ,下面例子通过点击事件toggle且护肩show的真假值,来处理显示。
<script src="https://how2j.cn/study/vue.min.js"></script>
<div id="div1">
<button v-on:click="toggle">切换隐藏显示</button>
<div v-if="show"> 默认这一条是看得见的</div>
</div>
<script>
new Vue({
el: '#div1',
data: {
show:true
},
methods:{
toggle: function(){
this.show=!this.show;
}
}
})
</script>
v-else,挨着写在v-if的下面,达到else 的目的,同样的还有v-else-if,用在两者中间。
v-for
也是顾名思义的哈,data传数据,然后for遍历。
<tr v-for="hero,index in heros"> 这样写的话可以获取遍历的下标
<div v-for="i in 10"> 这样就没得数据,就是纯数字的遍历
<script src="https://how2j.cn/study/vue.min.js"></script>
<style>
table tr td{
border:1px solid gray;
}
table{
border-collapse:collapse;
width:300px;
}
tr.firstLine{
background-color: lightGray;
}
</style>
<div id="div1">
<table align="center" >
<tr class="firstLine">
<td>name</td>
<td>hp</td>
</tr>
<tr v-for="hero in heros">
<td>{{hero.name}}</td>
<td>{{hero.hp}}</td>
</tr>
</table>
</div>
<script>
var data = [
{name:"盖伦",hp:341},
{name:"提莫",hp:225},
{name:"安妮",hp:427},
{name:"死歌",hp:893}
];
new Vue({
el: '#div1',
data: {
heros:data
}
})
</script>
v-bind属性绑定
本来是 v-bind:href, 可以简写成 :href
不只是可以绑定给超链哈,可以绑定任意属性。
<script src="https://how2j.cn/study/vue.min.js"></script>
<div id="div1">
<a v-bind:href="page">http://12306.com</a>
</div>
<script>
new Vue({
el: '#div1',
data:{
page:'http://12306.com'
}
})
</script>
v-model双向绑定
前面的例子,都是把 Vue对象上的数据显示在视图上,那么如何把视图上的数据放到Vue对象上去呢?
这时就需要用到v-model进行双向绑定
也就是bind是内到外,model是外到内
像这样,当input里面的值发生变化的时候,就会自动把变化后的值,绑定到Vue对象上去了
<script src="https://how2j.cn/study/vue.min.js"></script>
<div id="div1">
hero name: <input v-model="name" >
<button @click="doClick" >提交数据</button>
</div>
<script>
new Vue({
el: '#div1',
data:{
name:"teemo"
},
methods:{
doClick:function(){
alert(this.name);
}
}
})
</script>
computed计算属性
意思就是比methods多个返回值,在html中直接写方法名就行了。 如果使用methods的话得在html中写:方法名() ,带了个括号。
computed 和 methods 的区别
computed 是有缓存的,只要rmb没有变化,dollar 会直接返回以前计算出来的值,而不会再次计算。 这样如果是复杂计算,就会节约不少时间。
而methods每次都会调用
<script src="https://how2j.cn/study/vue.min.js"></script>
<style>
table tr td{
border:1px solid gray;
padding:10px;
}
table{
border-collapse:collapse;
width:800px;
table-layout:fixed;
}
tr.firstLine{
background-color: lightGray;
}
</style>
<div id="div1">
<table align="center" >
<tr class="firstLine">
<td>人民币</td>
<td>美元</td>
</tr>
<tr>
<td align="center" colspan="2">
汇率: <input type="number" v-model.number="exchange" />
</td>
</tr>
<tr>
<td align="center">
¥: <input type="number" v-model.number = "rmb" />
</td>
<td align="center">
$: {{ dollar }}
</td>
</tr>
</table>
</div>
<script>
new Vue({
el: '#div1',
data: {
exchange:6.4,
rmb:0
},
computed:{
dollar:function() {
return this.rmb / this.exchange;
}
}
})
</script>
watch监听属性
vue可以通过watch来监听属性值的变化。
比如上面那个列子就可以这样写:
watch:{
rmb:function(val) {
this.rmb = val;
this.dollar = this.rmb / this.exchange;
},
dollar:function(val) {
this.dollar = val;
this.rmb = this.dollar * this.exchange;
},
}
filter过滤器
定义一个 首字母大写 过滤器
然后在视图里如下方式使用:
{{ data|capitalize }}
这个 | 有点想linux的管道(还是重定向?有点忘了) 反正就把前一个的结果拿给下一个用,比如需要有多个过滤器的时候就这样写:
{{ data|capitalize|capitalizeLastLetter }}
<script src="https://how2j.cn/study/vue.min.js"></script>
<style>
table tr td{
border:1px solid gray;
padding:10px;
}
table{
border-collapse:collapse;
width:800px;
table-layout:fixed;
}
tr.firstLine{
background-color: lightGray;
}
</style>
<div id="div1">
<table align="center" >
<tr class="firstLine">
<td>输入数据</td>
<td>过滤后的结果</td>
</tr>
<tr>
<td align="center">
<input v-model= "data" />
</td>
<td align="center">
{{ data|capitalize }}
</td>
</tr>
</table>
</div>
<script>
new Vue({
el: '#div1',
data: {
data:''
},
filters:{
capitalize:function(value) {
if (!value) return '' //如果为空,则返回空字符串
value = value.toString()
return value.charAt(0).toUpperCase() + value.substring(1)
}
}
})
</script>
在上面的例子里可以看到,过滤器是定义在Vue对象里的。 但是有时候,很多不同的页面都会用到相同的过滤器,如果每个Vue对象里都重复开发相同的过滤器,不仅开发量增加,维护负担也增加了。
所以就可以通过全局过滤器的方式,只定义一次过滤器,然后就可以在不同的Vue对象里使用了。
注册全局过滤器:
Vue.filter('capitalize', function (value) {
if (!value) return ''
value = value.toString()
return value.charAt(0).toUpperCase() + value.slice(1)
})
Vue.filter('capitalizeLastLetter', function (value) {
if (!value) return '' //如果为空,则返回空字符串
value = value.toString()
return value.substring(0,value.length-1)+ value.charAt(value.length-1).toUpperCase()
})
组件
如效果所示,每个产品展示,就是一个模板。 只用做一个模板,然后照着这个模板,传递不同的参数就可以看到不同的产品展示了。
这个模板,就是组件。
先来个简单点的例子:
component的就是整个组件,然后template就是模板。
<script src="https://how2j.cn/study/vue.min.js"></script>
<style>
div.product{
float:left;
border:1px solid lightGray;
width:200px;
margin:10px;
cursor: pointer;
}
</style>
<div id="div1">
<product name="MAXFEEL休闲男士手包真皮手拿包大容量信封包手抓包夹包软韩版潮"></product>
<product name="宾度 男士手包真皮大容量手拿包牛皮个性潮男包手抓包软皮信封包"></product>
<product name="唯美诺新款男士手包男包真皮大容量小羊皮手拿包信封包软皮夹包潮"></product>
</div>
<script>
Vue.component('product', {
props:['name'],
template: '<div class="product" >{{name}}</div>'
})
new Vue({
el: '#div1'
})
</script>
加上个 遍历json数组:
大部分时候是拿到一个 json 数组,然后遍历这个 json 数组为多个组件实例。
<script src="https://how2j.cn/study/vue.min.js"></script>
<style>
div.product{
float:left;
border:1px solid lightGray;
width:200px;
margin:10px;
cursor: pointer;
}
</style>
<div id="div1">
<product v-for="item in products" v-bind:product="item"></product>
</div>
<script>
Vue.component('product', {
props:['product'],
template: '<div class="product" v-on:click="increaseSale">{{product.name}} 销量: {{product.sale}} </div>',
methods:{
increaseSale:function(){
this.product.sale++
}
}
})
new Vue({
el: '#div1',
data:{
products:[
{"name":"MAXFEEL休闲男士手包真皮手拿包大容量信封包手抓包夹包软韩版潮","sale":"18"},
{"name":"宾度 男士手包真皮大容量手拿包牛皮个性潮男包手抓包软皮信封包","sale":"35"},
{"name":"唯美诺新款男士手包男包真皮大容量小羊皮手拿包信封包软皮夹包潮","sale":"29"}
]
}
})
</script>
自定义指令
像 v-if, v-bind, v-on 等等前面学习的指令,都是 vus.js 自带的指令,那么除了这些指令,开发者还可以开发自定义的指令,比如 v-xart 来做一些效果。
如效果所示, 一旦使用了 v-xart 这个指令,那么文字颜色就会变成粉红,后面也会自动加上 (x-art)
自定义指令的方式:
1. 使用Vue.directive 来自定义
2. 第一个参数就是 指令名称 xart
3. el 表示当前的html dom对象
4. 在方法体内就可以通过 innerHTML style.color 等方式操控当前元素了
<script src="https://how2j.cn/study/vue.min.js"></script>
<div id="div1">
<div v-xart> 好好学习,天天向上 </div>
</div>
<script>
Vue.directive('xart', function (el) {
el.innerHTML = el.innerHTML + ' ( x-art ) '
el.style.color = 'pink'
})
new Vue({
el: '#div1'
})
</script>
上面例子是不带参数的,现在带上参数
binding.value 就是指 v-xart=“xxx” 这个xxx。 此时xxx是一个json对象,所以就可以通过.text, .color取出对应的值出来。
Vue.directive('xart', function (el,binding) {
el.innerHTML = el.innerHTML + '( ' + binding.value.text + ' )'
el.style.color = binding.value.color
})
然后有个钩子函数的知识点,看不懂就先不总结了。
Ajax框架
一般说来 Vue 不会直接使用原生的 Ajax 而是使用 ajax 框架。 而 fetch.js 就是眼下比较流行的一种 ajax 框架
<script src="https://how2j.cn/study/fetch.min.js"></script>
<div id="hero">
</div>
<script>
var url = "http://how2j.cn/study/json.txt"
fetch(url).then(function(response) {
response.json().then(function (jsonObject) {
var jsonString = JSON.stringify(jsonObject)
document.getElementById("hero").innerHTML = "通过fetch获取到的json数据:"+ jsonString;
})
}).catch(function(err){
console.log("Fetch错误:"+err);
})
</script>
新的知识点是在 mounted 的时候进行。 mounted 表示 Vue 对象加载成功了。
<script src="https://how2j.cn/study/vue.min.js"></script>
<script src="https://how2j.cn/study/fetch.min.js"></script>
<head>
<style>
table tr td{
border:1px solid gray;
}
table{
border-collapse:collapse;
width:300px;
}
tr.firstLine{
background-color: lightGray;
}
</style>
</head>
<div id="div1">
<table align="center" >
<tr class="firstLine">
<td>name</td>
<td>hp</td>
</tr>
<tr v-for="hero in heros">
<td>{{hero.name}}</td>
<td>{{hero.hp}}</td>
</tr>
</table>
</div>
<script>
var url = "http://how2j.cn/study/jsons.txt";
new Vue({
el:'#div1',
data:{
heros:[]
},
mounted:function(){ //mounted 表示这个 Vue 对象加载成功了
self=this
fetch(url).then(function(response) {
response.json().then(function (jsonObject) {
self.heros = jsonObject
})
}).catch(function(err){
console.log("Fetch错误:"+err);
})
}
})
</script>
最后还要注意的是,vue的代码对格式的要求挺高,少个逗号、错个符号就整不了了,要注意的。