3.Vue进阶
3.1 Vue方法、计算属性及监听器
3.1.1 computed 计算属性
computed用于定义计算属性,计算属性是基于他们的依赖关系进行缓存的,只有当依赖的数据发生变化时,计算属性才会重新计算。
数据不发生变化:
<body>
<div id="app">
{{ msg }}
<br>
{{ reversedMsg }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
msg: 'hello world!'
}
},
computed: {
reversedMsg() {
// split()用于将字符串分割成子字符串数组。
// reverse()用于反转数组元素的顺序。
//join()用于将数组元素合并成一个字符串。
return this.msg.split('').reverse().join('')
}
}
}).mount('#app')
</script>
</body>
数据发生变化:
<body>
<div id="app">
商品名称:小米手机<br>
商品数量:<button @click="sub">-</button>{{ num }}<button @click="add">+</button><br>
总价:{{ total }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
num: 1
}
},
computed: {
total() {
return this.num * 5000
}
},
methods: {
sub() {
if (this.num > 1) this.num--
else this.num = 1
},
add() {
this.num++
}
}
}).mount('#app')
</script>
</body>
对数据进行再过滤处理:
<body>
<div id="app">
{{ newMoney }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
money: 1000
}
},
computed: {
newMoney(){
return this.money + '¥'
}
}
}).mount('#app')
</script>
</body>
3.1.2 methods 方法
methods
是一个对象,用于定义组件的方法。这些方法可以在模板中调用,也可以在组件的其他部分(如生命周期钩子、计算属性等)中使用。
<body>
<div id="app">
{{ msg }}
<br>
{{ reversedMsg() }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
msg: 'hello world!'
}
},
methods: {
reversedMsg() {
return this.msg.split('').reverse().join('')
}
}
}).mount('#app')
</script>
</body>
computed
与 methods
的区别:
- 缓存:
computed
有缓存,methods
没有缓存。 - 调用方法:
computed
在模板中使用时不需要括号,methods
需要括号。 - 适用场景:
computed
适用于依赖其他数据动态计算出的数据,methods
适用于需要执行任何逻辑的场景。
3.1.3 watch 监听
watch
用于观察和响应数据的变化。当你需要在数据变化时执行一些操作,例如发送网络请求、更新其他数据等,可以使用 watch
。
3.1.3.1 watch
的基本用法
watch
是一个对象,键是需要观察的表达式,值是对应的回调函数。回调函数有两个参数:新值和旧值。
<body>
<div id="app">
商品名称:小米手机<br>
商品数量:<button @click="sub">-</button>{{ num }}<button @click="add">+</button><br>
总价:{{ total }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
num: 1
}
},
computed: {
total() {
return this.num * 5000
}
},
methods: {
sub() {
this.num--
},
add() {
this.num++
}
},
watch: {
num(newVal, oldVal) {
this.num = newVal <= 0 ? oldVal : newVal
}
}
}).mount('#app')
</script>
</body>
深度监听:
当需要监听一个对象的属性变化,可以使用 deep
选项进行深度监听。这样,当监听的对象或数组内部发生变化时,回调函数也会被触发。
<body>
<div id="app">
商品名称:{{goods.name}}<br>
商品数量:<button @click="sub">-</button>{{ goods.num }}<button @click="add">+</button><br>
总价:{{ total }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
goods: {
name: '小米手机',
num: 1
}
}
},
computed: {
total() {
return this.goods.num * 5000
}
},
methods: {
sub() {
this.goods.num--
},
add() {
this.goods.num++
}
},
watch: {
goods: {
handler(newVal, oldVal) {
console.log(newVal, oldVal)
this.goods.num = newVal.num
},
deep: true
}
}
}).mount('#app')
</script>
</body>
注意事项
- 性能影响:深度监听会对性能产生一定影响,因为它需要递归地遍历对象或数组的每个属性。因此,在不需要深度监听的情况下,尽量避免使用
deep: true
。 - 数组变化:深度监听可以监听到数组内部元素的变化,例如通过
push
、pop
、splice
等方法修改数组。
上述代码当数量小于1是时仍能继续减,解决方案:
<body>
<div id="app">
商品名称:{{goods.name}}<br>
商品数量:<button @click="sub">-</button>{{ goods.num }}<button @click="add">+</button><br>
总价:{{ total }}
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
goods: {
name: '小米手机',
num: 1
}
}
},
computed: {
total() {
return this.goods.num * 5000
},
goodsStr() {
// JSON.stringify() 方法用于将一个 JavaScript 对象或值转换为一个 JSON 字符串。 JSON 字符串是一种轻量级的数据交换格式。
return JSON.stringify(this.goods)
}
},
methods: {
sub() {
this.goods.num--
},
add() {
this.goods.num++
}
},
watch: {
goodsStr(newVal, oldVal) {
// JSON.parse() 方法用于将一个 JSON 字符串转换为一个 JavaScript 对象。
let newGoods = JSON.parse(newVal)
let oldGoods = JSON.parse(oldVal)
this.goods.num = newGoods.num <= 0 ? 1 :newGoods.num
}
}
}).mount('#app')
</script>
</body>
3.2 Vue的表单绑定
3.2.1 v-model 实现表单绑定
<body>
<div id="app">
<h3>注册</h3>
<form>
姓名:<input type="text" v-model="user.name"><br>
密码:<input type="password" v-model="user.password"><br>
确认密码:<input type="password" v-model="user.begin"><br>
性别:<input type="radio" v-model="user.sex" value="0">男
<input type="radio" v-model="user.sex" value="1">女<br>
爱好:<input type="checkbox" v-model="user.like" value="0">吃饭
<input type="checkbox" v-model="user.like" value="1">睡觉
<input type="checkbox" v-model="user.like" value="2">打豆豆<br>
国籍:<select v-model="user.nationality">
<option value="0">中国</option>
<option value="1">美国</option>
<option value="2">英国</option>
</select><br>
个人简介:<textarea cols="30" rows="10" v-model="user.brief"></textarea><br>
<input type="button" @click="register" value="注册">
</form>
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
user: {
name: '',
password: '',
begin: '',
sex: 0,
like: [],
nationality: 0,
brief: ''
}
}
},
methods: {
register() {
console.log(this.user)
}
}
}).mount('#app')
</script>
</body>
3.2.2 v-model 修饰符
常见的修饰符:
- .lazy: 默认情况下,
v-model
会在输入框的input
事件中同步输入框的值。使用.lazy
修饰符后,v-model
会在change
事件中同步输入框的值,即输入框失去焦点后才更新数据。 - .trim: 使用
.trim
修饰符后,v-model
会自动去除输入框两端的空格。 - .number: 使用
.number
修饰符后,v-model
会将输入框的值转换为数值类型
<body>
<div id="app">
<!-- v-model.lazy 指令可以实现输入框失去焦点后才更新数据 -->
{{ num }} <input type="text" v-model.lazy="num"><br>
<!-- v-model.trim 指令可以自动去除输入框两端的空格 -->
<input type="text" v-model.trim="msg"><button @click="submit">提交</button><br>
<!-- v-model.number 指令可以将输入框的值转换为数值类型 -->
{{ num + 1}} <input type="text" v-model.number="num">
</div>
<script src="../js/vue3.js"></script>
<script>
Vue.createApp({
data() {
return {
num: 10,
msg: 'hello'
}
},
methods: {
submit() {
console.log(this.msg)
}
}
}).mount('#app')
</script>
</body>
标签:学习,goods,return,methods,Vue,---,num,Vue3,computed
From: https://www.cnblogs.com/yishengwanwuzhao/p/18331172