【vue2.x(二)】vue模版语法(下)


承接上节内容 【vue2.x(二)】vue模版语法(上),继续介绍vue模版语法。

v-if/v-show

用来控制元素显示或隐藏,属性为布尔值。

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title>关注微信公众号【程序员战羽】</title>
		<script src="../js/vue.js" type="text/javascript" charset="utf-8"></script>
	</head>
	<body>
		<!-- 关注微信公众号【程序员战羽】,获取更多技术文章 -->
		<div id="app">
			<button type="button" @click="isShow =!isShow">改变isShow的值</button>
			<p v-if="isShow">该元素被v-if控制是否显示</p>
			<p v-show="isShow">该元素被v-show控制是否显示</p>
			
			<p v-if='num>0.7'>范围大于0.7的显示</p>
			<p v-else-if="0.5<num<=0.7">范围在0.5到0.7的显示</p>
			<p v-else>范围小于等于0.5显示</p>
		</div>
		<script type="text/javascript">
			const app = new Vue({
				el:'#app',
				data:{
					isShow:true,
					num:Math.random()  //随机生成0-1范围内的数字
				}
			})
		</script>
	</body>
</html>

v-if 和 v-show 的区别:

  • 控制元素显示或隐藏实现原理不同:

    v-if 会动态地创建或移除 DOM 元素。

    v-show 会动态为元素添加或移除 style=“display: none;” 样式。

  • 性能消耗不同:

    v-if 有更高的切换开销,而 v-show 有更高的初始渲染开销。

    若需要非常频繁地切换,则使用 v-show 较好;若在运行时条件很少改变,则使用 v-if 较好。

v-for

实现页面列表渲染,常用来循环数组。

v-for索引: 可选参数,表示当前项的索引。

v-for的key: 正确维护列表的状态,并能复用现有的DOM元素,提升渲染的性能。

key的注意事项:

①key 的值只能是字符串或数字类型

②key 的值必须具有唯一性(即:key 的值不能重复)

③ 建议把数据项 id 属性的值作为 key 的值( id 具有唯一性)

④ 使用 index 的值当作 key 的值没有任何意义(index 不具有唯一性)

⑤ 建议使用 v-for 指令时一定要指定 key 的值(既提升性能、又防止列表状态紊乱)

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title>关注微信公众号【程序员战羽】</title>
		<script src="../js/vue.js" type="text/javascript" charset="utf-8"></script>
	</head>
	<body>
	    <!-- 关注微信公众号【程序员战羽】,获取更多技术文章 -->
		<div id="app">
			<ul>
				<li v-for="(hot,index) in baiduHotList" :key="hot.id">
					{{hot.id}} {{hot.title}}
				</li>
			</ul>
		</div>
		<script type="text/javascript">
			let app = new Vue({
				el: '#app',
				data: {
					baiduHotList: [{
							id: 1,
							title: '热点新闻一'
						},
						{
							id: 2,
							title: '热点新闻二'
						},
						{
							id: 3,
							title: '热点新闻三'
						}
					]
				}
			})
		</script>
	</body>
</html>

表单输入绑定

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title>关注微信公众号【程序员战羽】</title>
		<script src="../js/vue.js" type="text/javascript" charset="utf-8"></script>
	</head>
	<body>
		<!-- 关注微信公众号【程序员战羽】,获取更多技术文章 -->
		<div id="app">
			<form @submit.prevent="submit">
				账号:<input type="text" v-model.trim="userInfo.account"> <br /><br />
				密码:<input type="password" v-model="userInfo.password"> <br /><br />
				年龄:<input type="number" v-model.number="userInfo.age"> <br /><br />
				性别:
				男<input type="radio" name="sex" v-model="userInfo.sex" value="male">
				女<input type="radio" name="sex" v-model="userInfo.sex" value="female"> <br /><br />
				爱好:
				学习<input type="checkbox" v-model="userInfo.hobby" value="study">
				打游戏<input type="checkbox" v-model="userInfo.hobby" value="game">
				吃饭<input type="checkbox" v-model="userInfo.hobby" value="eat">
				<br /><br />
				学校所在地区
				<select v-model="userInfo.city">
					<option value="">请选择地区</option>
					<option value="beijing">北京</option>
					<option value="shanghai">上海</option>
					<option value="shenzhen">深圳</option>
					<option value="wuhan">武汉</option>
				</select>
				<br /><br />
				其他信息:
				<textarea v-model.lazy="userInfo.other"></textarea> <br /><br />
				<input type="checkbox" v-model="userInfo.agree">阅读并接受<a
					href="http://www.baidu.com">《用户协议》</a><br /><br />
				<button>提交</button>
			</form>
		</div>
		<script type="text/javascript">
			Vue.config.productionTip = false //关闭控制台提示
			const app = new Vue({
				el: '#app',
				data: {
					userInfo: {
						account: '',
						password: '',
						age: 20,
						sex: 'female',
						hobby: [],
						city: 'beijing',
						other: '',
						agree: ''
					}
				},
				methods: {
					submit() {
						console.log(JSON.stringify(this.userInfo))
					}
				}
			})
		</script>
	</body>
</html>

computed计算属性 /watch状态监听

computed计算属性存在缓存机制,只有当其依赖的响应式数据发生变化时才会清空缓存重新计算结果。

缓存机制本质:由dirty属性控制,当dirty为true时,会重新计算结果。dirty只有当其响应式数据发送变化时设置为true,重新计算后会被重置为false。

<!DOCTYPE html>
<html lang="en">
	<head>
		<meta charset="UTF-8">
		<title>关注微信公众号【程序员战羽】</title>
		<script src="../js/vue.js" type="text/javascript" charset="utf-8"></script>
	</head>
	<body>
		<!-- 关注微信公众号【程序员战羽】,获取更多技术文章 -->
		<div id="app">
			<button @click="changeNum">更新Num的值</button><br><br>
			<button @click="getComputedNum">输出computedNum的值</button><br><br>
			<input type="text" v-model="name" />
		</div>
		<script>
			const app = new Vue({
				el: '#app',
				data: {
					num: 0,
					name:'程序员战羽'
				},
				methods: {
					changeNum() {
						this.num++;
					},
					getComputedNum() {
						console.log(this.computedNum);
					}
				},
				computed: {
					computedNum() {
						return this.num + '-' + Math.random()
					}
				},
				watch: { //监听用户修改的动作
					name(newValue, oldValue) {
						console.log(newValue, oldValue)
					}
				}
			})
		</script>
	</body>
</html>

filters过滤器

filters过滤器:在页面中直接操作数据,返回最终结果(并没有改变原本的数据, 是产生新的对应的数据)。常用于文本的格式化。

过滤器用于两处:插值表达式和 v-bind 属性绑定。

过滤器应该被添加在 JavaScript 表达式的尾部,由“管道符”进行调用。

注意:过滤器仅在 vue 2.x 和 1.x 中受支持,在 vue 3.x 的版本中剔除了过滤器相关的功能。

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title>关注微信公众号【程序员战羽】</title>
		<script src="../js/vue.js" type="text/javascript" charset="utf-8"></script>
	</head>
	<body>
		<!-- 
			过滤器:
				定义:对要显示的数据进行特定格式化后再显示(适用于一些简单逻辑的处理)。
				语法:
						1.注册过滤器:Vue.filter(name,callback) 或 new Vue{filters:{}}
						2.使用过滤器:{{ xxx | 过滤器名}}  或  v-bind:属性 = "xxx | 过滤器名"
				备注:
						1.过滤器也可以接收额外参数、多个过滤器也可以串联
						2.并没有改变原本的数据, 是产生新的对应的数据
		-->
		<div id="app">
			<!-- 在双括号中通过管道符调用capitalize过滤器,对message值进行格式化 -->
			<!-- 在v-bind中通过管道符调用capitalize过滤器,对info值进行格式化 -->
			<p :title="info | capitalize">{{message | capitalize}}</p>
			<!-- 过滤器串联、过滤器不传参 -->
			<p :title="info | capitalize">{{message | capitalize | maxLength}}</p>
			<!-- 过滤器串联、过滤器传参 -->
			<p :title="info | capitalize">{{message | capitalize | maxLength(5)}}</p>
		</div>
		<div id="app2">
			<p>{{name | capitalize}}</p>
		</div>
		<!-- 全局过滤器 独立于每个VM实例之外-->
		<script>
			// 首字母大写
			Vue.filter('capitalize', (str) => {
				return str.charAt(0).toUpperCase() + str.slice(1) + '~~~'
			})

			// 定义控制文本长度的过滤器(有参数len)
			Vue.filter('maxLength', (str, len = 10) => {
				if (str.length <= len) return str
				return str.slice(0, len) + '...'
			})
		</script>
		<script>
			// 需求:首字母大写
			const vm = new Vue({
				el: '#app',
				data: {
					message: 'hello zhanyu',
					info: 'title zhanyu',
				},
				// 私有过滤器,只能被当前 vm 所控制的区域所使用
				filters: {
					capitalize(str) {
						return str.charAt(0).toUpperCase() + str.slice(1)
					}
				}
			})
		</script>
		<script>
			const vm2 = new Vue({
				el: '#app2',
				data: {
					name: 'zhanyu'
				}
			})
		</script>
	</body>
</html>

自定义指令

vue 官方除了提供 v-for、v-model、v-show等常用内置指令,也允许注册自定义指令。

1、用途:用来操作DOM元素。虽然官方推荐数据驱动视图,但有时还是需要自定义指令来操作DOM。

2、可分为两类:局部自定义指令与全局自定义指令。

3、语法

局部指令:
new Vue({
	directives:{指令名:配置对象} 或 directives:{指令名:回调函数}
}) 
全局指令:
Vue.directive(指令名,配置对象) 或 Vue.directive(指令名,回调函数)

4、钩子函数(在特定阶段执行相关的操作)

一个指令定义对象可以提供如下几个钩子函数 (均为可选):

bind:指令与元素成功绑定时调用【只执行1次】。

inserted:指令所在元素被插入页面时调用【只触发一次】。

update:指令所在模板结构被重新解析时调用【可能触发多次】。

5、注意

指令定义时不加v-,但使用时要加v-。

指令名称要使用kebab-case命名规范。

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title>关注微信公众号【程序员战羽】</title>
		<script src="../js/vue.js" type="text/javascript" charset="utf-8"></script>
	</head>
	<body>
		<!-- 关注微信公众号【程序员战羽】,获取更多技术文章 -->
		<div id="app">
			<input type="text" v-custom-bind:value="message"><br><br>
			<!-- <input type="text" v-custombind:value="message"><br><br> -->
			<div v-demo:foo.a.b="message"></div>
		</div>
		<script type="text/javascript">
			//定义全局指令
			// Vue.directive('custom-bind',{
			// 	bind(element,binding){
			// 		element.value = binding.value
			// 	},
			// 	inserted(element,binding){
			// 		element.focus()
			// 	},
			// 	update(element,binding){
			// 		element.value = binding.value
			// 	}
			// })
			Vue.directive('demo',{
				bind:function(el,binding,vnode){
					console.log(el)
					console.log(binding)
					console.log(vnode)
					el.innerHTML =
					      'name: '       + binding.name + '<br>' +
					      'value: '      + binding.value + '<br>' +
					      'expression: ' + binding.expression + '<br>' +
					      'argument: '   + binding.arg + '<br>' +
					      'modifiers: '  + JSON.stringify(binding.modifiers) + '<br>' +
					      'vnode keys: ' + Object.keys(vnode).join(', ')
				}
			})
			
			const app = new Vue({
				el: '#app',
				data: {
					message:'程序员战羽'
				},
				// 定义局部指令
				directives:{
					'custom-bind':{
						bind:function(element,binding){
							element.value = binding.value
						},
						// bind(element,binding){
						// 	element.value = binding.value
						// },
						inserted(element,binding){
							element.focus()
						},
						update(element,binding){
							element.value = binding.value
						}
					},
					//在 bind 和 update 时触发相同行为,可以简写如下
					// 'custom-bind':function(el,binding){
					// 	el.style.backgroundColor = 'red'
					// }
					// 'custom-bind'(el,binding){
				    // 	el.style.backgroundColor = 'red'
				    // }
					// custombind(el,binding){
					// 	el.style.backgroundColor = 'red'
					// }
				}
			})
		</script>
	</body>
</html>

微信扫码关注微信公众号【程序员战羽】
获取更多技术内容

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

和光同其尘

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值