Vue: 模板、指令与操作符
模板 template 三种写法
Vue 完整版,写在 HTML 里
index.html:
<div id=xxx>
{{n}}
<button @click= "add">+1< /button>
</div>
main.js的new Vue()
的options里就不需要写template属性:
new Vue({
el: '#xxx'
data:{n:0}, // data可以改成函数
methods:{add(){}}
})
Vue 完整版,写在选项里
在index.html里写好挂载点:
<div id="app"></div>
main.js的new Vue()
的options里写template属性:
new Vue({
template: `
<div>
{{n}}
<button @click= "add">+1</button>
</div>`,
data: { n: 0 },
methods: {
add() {
this.n += 1;
},
},
}).$mount("#app");
// 注意一个细节: div#app会被替代
Vue 非完整版,配合 xxx.vue 文件
xxx.vue
<template>
<div>
{{n}}
<button @click="add">
+1
</button>
</div>
</template>
<script>
export default {
data(){ return {n:0} }, // data必须为函数
methods:{add(){ this.n += 1 } }
}
</script>
<style>这里写CSS </style>
main.js
import Xxx from './xxx. vue')
// Xxx是一个options对象
new Vue({
render: h => h(Xxx) //视图用render
}).$mount('#app')
模板中的语法
我们把HTML模板叫做template
展示内容
表达式
{{ object.a }}
表达式{{ n + 1 }}
可以写任何运算{{ fn(n) }}
可以调用函数- 如果值为undefined或null就不显示
- 另一种写法为
<div v-text="表达式"></div>
基本没人用这种写法
HTML 内容
- 假设 data.x 值为
<strong>hi</strong>
<div v-html="x"></div>
即可显示粗体的 hi
我就想展示{{n}}
<div v-pre>{{ n }}</div>
- v-pre 不会对模板进行编译
绑定属性
- 绑定 src
<img v-bind:src="x" />
- v-bind: 简写为
<img :src="x" />
- 绑定对象
<div
:style="{border: '1px solid red', height: 100}">
<!-- 注意这里可以把'100px'写成100 -->
</div>
绑定事件
v-on:事件名
// 事件处理函数可以为函数名
<button v-on:click="add">+1</button> //点击之后,Vue会运行add()
// 事件处理函数可以为函数名加参数
<button v-on:click="xxx(1)">xxx</button> //点击之后,Vue会运行xxx(1)
// 事件处理函数可以为直接执行的代码
<button v-on:click="n+=1">xxx</button> //点击之后,Vue会运行n+=1
- 即发现函数就加括号调用之,否则就直接运行代码
- 缩写
<button @click="add">+1</button>
正常人都用缩写
条件判断
- if…else
<div v-if="x > 0">
x大于0
</div>
<div v-else-if="x===">
x为0
</div>
<div v-else>
x小于0
</div>
循环
- for (value, key) in 对象或数组
<ul>
<li v-for="(u, index) in users" :key="index">
索引: {{index}} 值: {{u. name}}
</li>
</ul>
<ul>
<li v-for="(value, name) in obj" :key="name">
属性名: {{name}}, 属性值: {{value}}
</li>
</ul>
注意: 每个v-for后面一定要接一个 :key,否则会有警告。
显示、隐藏
- v-show
<div v-show="n%2===0">n是偶数</div>
- 近似等于
<div :style="{display:n%2===0 ? 'block': 'none'}">n是偶数</div>
但是要注意,看得见的元素display不只有block,如table的display为table,如li的display为list-item
总结
Vue模板主要特点有:
- 使用XML语法(不是HTML)
- 使用 {{}} 插入表达式
- 使用 v-html、 v-on、 v-bind等指令操作DOM
- 使用 v-if、 v-for等指令实现条件判断和循环
其他指令
指令 directive
什么是指令
- 以 v- 开头的东西就是指令
<div v-text="x"></div>
<div v-html="x"></div>
语法
v-指令名:参数=值
,如v-on:click=add
- 如果值里没有特殊字符,则可以不加引号
- 有些指令没有参数和值,如 v-pre
- 有些指令没有值,如
v-on:click.prevent
修饰符
有些指令支持修饰符
@click.stop="add"
表示阻止事件传播/冒泡@click.prevent="add"
表示阻止默认动作@click.stop.prevent=“add"
同时表示上述两种意思
一共有多少修饰符呢
加粗的比较重要
v-on 支持的有:
.{keycode | keyAlias}, .stop, .prevent, .capture, .self, .once, .passive, .native
- 快捷键相关:
.ctrl, .alt, .shift, .meta, .exact
- 鼠标相关:
.left, .right, .middle
v-bind 支持的有:
.prop, .camel, .sync
v-model 支持的有:
.lazy, .number, .trim
.sync 修饰符
场景描述
Q: 爸爸给儿子钱,儿子要花钱怎么办,示例
A: 儿子打电话(触发事件)向爸爸要钱
main.js
// 此处是非完整版vue
import Vue from "vue";
import App from "./App.vue";
Vue.config.productionTip = false;
new Vue({
render: h => h(App)
}).$mount(“#app”);
App.vue
<template>
<div class="app">
App.vue 我现在有 {{total}}
<hr>
<!-- 关键看这里 -->
<Child :money="total" v-on:update:money="total = $event"/>
</div>
</template>
<script>
import Child from "./Child.vue";
export default {
data() {
return { total: 10000 };
},
components: { Child: Child }
};
</script>
<style>
.app {
border: 3px solid red;
padding: 10px;
}
</style>
Child.vue
<template>
<div class="child">
{{money}}
<!-- 关键看这里 -->
<button @click="$emit('update:money', money-100)">
<span>花钱</span>
</button>
</div>
</template>
<script>
export default {
props: ["money"]
};
</script>
<style>
.child {
border: 3px solid green;
}
</style>
- Vue规则: 组件不能修改props外部数据
- Vue规则:
this.$emit
可以触发事件,并传参 - Vue规则:
$event
可以获取$emit
的参数
由于这种场景很常见
- 尤雨溪发明了
.sync
,修改后的示例
// App.vue
:money.sync="total"
// 等价于
:money.sync="total" v-on:update:money="total"=$event
扩展阅读:
总结
搞清楚下面这 4 个修饰符就行了
@click.stop=“xxx"
@click.prevent="xxx"
@keypress.enter="xxx"
:money.sync="total"