首页 > 其他分享 >vue 封装密码输入框(屏蔽浏览器反显,禁止粘贴)

vue 封装密码输入框(屏蔽浏览器反显,禁止粘贴)

时间:2023-01-16 10:23:16浏览次数:50  
标签:el vue val oldPwd value 输入框 let 反显 event

vue 封装密码输入框(屏蔽浏览器反显,禁止粘贴)

 

备注:使用了ant-design-vue,可以换其他组件输入框或原生

<template>
  <a-input
    style="ime-mode: disabled"
    :value="hideValue"
    @change="valueChange"
    @compositionstart="compositionstartHandle"
    @compositionend="compositionendHandle"
    @paste.capture.prevent="pasteHandle"
    ref="password-input"
    :placeholder="placeholder"
  >
    <a-icon @click="isHidden = !isHidden" v-if="isHidden" slot="suffix" type="eye-invisible" style="color: rgba(0,0,0,.45)" />
    <a-icon @click="isHidden = !isHidden" v-else slot="suffix" type="eye" style="color: rgba(0,0,0,.45)" />
  </a-input>
</template>


<script>
export default {
  name: 'InputPassword',
  props: {
    value: {
      type: String,
    },
    placeholder: {
      type: String,
      default: '请输入',
    },
  },
  // model: {
  //   prop: 'value', //指向props的参数名
  //   event: 'input' //事件名称
  // },
  data() {
    return {
      hideValue: '',
      isHidden: true,
      compositionStatue: false,
      compositionStartCursorIndex: 0
    }
  },
  watch: {
    isHidden: {
      handler() {
        this.render(this.value)
      },
    },
    value: {
      handler(val) {
        this.render(val)
      },
    },
  },
  methods: {
    // 对输入框的显示hideValue进行渲染 val 是实际的value
    render(val) {
      if (!this.isHidden) {
        this.hideValue = val
      } else {
        this.hideValue = val.replace(/[^•]/g, '•')
      }
    },
    // 事件
    valueChange(event) {
      // console.log(event, 'zs------------jfsevent')
      // console.log(this.$refs['password-input'])
      // console.log(this.$refs['password-input'].selectionStart, 'zsselectionStart')
      if (this.compositionStatue) {
        // 进行中文输入时不执行 inputHandle 函数
        return false
      }
      let el = event.target
      // console.log(this.value, el, 'zs------------valueChange')
      // console.log(el.selectionStart, 'zs----elselectionStart')
      let oldPwd = this.value || ''
      let newPwd = ''
      let cursorIndex = el.selectionStart
      let val = el.value
      // console.log(el, val, cursorIndex,'zs--------val')
      if (this.isHidden) {
        // 删除字符
        if (oldPwd && oldPwd.length > val.length) {
          let delEndIndex = oldPwd.length - val.length + cursorIndex
          newPwd = oldPwd.substring(0, cursorIndex) + oldPwd.substring(delEndIndex)
        } else {
          let reg = /[^•]/.exec(val) // 获取虚假密码中新增的密码字符
          if (reg) {
            // 如果存在新增密码字符,则进行输入输入处理
            newPwd = this.insertStr(oldPwd, reg.index, reg[0]) // 将用户新输入的字符插入旧的真实密码
            this.cursorMove(el, reg.index + 1) // 设置光标的位置
          } else {
            // this.render() 二次触发
            // 如果不存在新增密码字符,不做改变
            newPwd = oldPwd
          }
        }
      } else {
        newPwd = el.value
      }
      this.$emit('input', newPwd)
    },
    /**
     * 根据位置在字符串中插入字符串
     * @params soure 原字符串
     * @params start 位置
     * @params newStr 要插入的字符串
     */
    insertStr(soure, start, newStr) {
      return soure.slice(0, start) + newStr + soure.slice(start)
    },
    /**
     * 控制光标的位置
     */
    cursorMove(elem, spos) {
      // spos 光标的位置 -1为最后一位
      if (spos < 0) spos = elem.value.length
      if (elem.setSelectionRange) {
        //兼容火狐,谷歌
        setTimeout(function () {
          elem.setSelectionRange(spos, spos)
          elem.focus()
        }, 0)
      } else if (elem.createTextRange) {
        //兼容IE
        var rng = elem.createTextRange()
        rng.move('character', spos)
        rng.select()
      }
    },


    compositionstartHandle(event) {
      // console.log(event,event.target)
      // this.compositionStartCursorIndex = this.$refs['password-input'].selectionStart // 记录进行中文输入时光标的位置
      this.compositionStartCursorIndex = event.target.selectionStart // 记录进行中文输入时光标的位置
      this.compositionStatue = true
    },


    compositionendHandle(event) {
      this.limitCN(event.target)
      this.compositionStatue = false
      this.compositionLength = 0
    },


    pasteHandle() {
      return false
    },


    // 限制中文输入
    limitCN(el) {
      // let val = this.$refs['password-input'].value; // 获取输入框中的值
      let val = el.value; // 获取输入框中的值
      // eslint-disable-next-line no-control-regex
      val = val.replace(/[^\x00-\x80•]/gi, '');
      
      el.value = val;
      this.cursorMove(
        el,
        this.compositionStartCursorIndex
      ); // 将光标重置为中文输入前的位置
    }
  },
}
</script>


<style lang='less' scoped>
</style>

ps: 参考了其他博客文档,忘记了链接。。。

标签:el,vue,val,oldPwd,value,输入框,let,反显,event
From: https://www.cnblogs.com/wyc-blog/p/17054792.html

相关文章