vue 自定义指令 自己实现 v-if 和 v-show

36 篇文章 8 订阅

一、自定义指令语法:

组件中使用

<template>
    <div>
    <input type="text" v-focus='123' >
    </div>
</template>
 
<script>
export default {
  directives: {
    focus: { // 自定义指令的名字
    // 下面每个方法都是一个钩子函数
    // el代表 当前绑定的dom元素
    // vnode 当前节点
      bind: (el, binding,vnode) => {
        el.value = 56 // 可以赋值 不能使用方法
        console.log('bind:只调用一次,指令第一次绑定到元素时调用。在这里可以进行一次性的初始化设置。')
      },
      inserted: (el, binding) => {
        el.focus() // 可以使用方法
        console.log('inserted:被绑定元素插入父节点时调用 (仅保证父节点存在,但不一定已被插入文档中)。')
      },
      update: (el, binding) => {
        console.log('update:被绑定元素所在模板更新时调用,模板还没更新完成')
      },
      componentUpdated: (el, binding) => {
        console.log('componentUpdated:指令所在组件的 VNode 及其子 VNode 全部更新后调用。')
      },
      unbind: (el, binding) => {
        console.log('unbind:只调用一次,指令与元素解绑时调用。')
      }
    }
  }
}
</script>

 全局注册 


export default {
  install (Vue) {
    Vue.directive('focus', {
      inserted: function (el, bind) {
        el.focus()
        console.log(el, bind)
      }
    })
  }
}
 
//main.js
import directive from './views/directive'
Vue.use(directive)

二、实现 v-show

v-show 就是把当前元素 设置display:none / block 来控制显隐

export default {
	install: (Vue) => {
		console.log(Vue);
		// 小程序里面不生效
		Vue.directive('myShow', function(el,binding, vnode) {
			if (!(binding.value)) {
				el.style.display = 'none'
			}else {
				el.style.display = 'block'
			}
		})
	}
}

三、实现v-if 

而 v-if 来把当前页面元素是否删除 

export default {
	install: (Vue) => {
		Vue.directive('myIf', // 下面每个方法都是一个钩子函数
			// el代表 当前绑定的dom元素
			(el, binding, vnode) => {
				// 判断传过来的值是为true 如果是false取反不显示
				if (!(binding.value)) {
					// 创建一个注释元素
					const comment = document.createComment(' ');
					// 设置value值
					Object.defineProperty(comment, 'setAttribute', {
						value: () => undefined,
			      });
					// 用注释节点替换 当前页面元素  
					vnode.elm = comment;
                    // 下面作为初始化操作 赋值为空
					vnode.text = ' ';
					vnode.isComment = true;
					vnode.context = undefined;
					vnode.tag = undefined;
					vnode.data.directives = undefined;

					// 判断当前元素是否是组件  如果是组件的话也替换成 注释元素
					if (vnode.componentInstance) {
						vnode.componentInstance.$el = comment;
					}

					// 判断当前元素是否是文档节点或者是文档碎片节点 
					if (el.parentNode) {
						// 从 DOM 树中删除 node 节点,除非它已经被删除了。
						el.parentNode.replaceChild(comment, el);
					}
				}
				console.log('bind:只调用一次,指令第一次绑定到元素时调用。在这里可以进行一次性的初始化设置。')
			})
	}
}

页面使用

<template> 
	<view class="content">
		<view v-red> 123111 </view>
		<view v-myIf="flag"> 
			123
		 </view>
		<Tab  v-myIf="flag"></Tab>
		<view v-myShow="flag">哦哦哦</view>
		<Tab  v-myShow="flag"></Tab>
	</view>
</template>

  • 7
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值