禁止浏览器记住密码和自动填充 element-ui+vue

news2024/11/27 11:48:51

vue 根据element-ui 自定义密码输入框,防止浏览器 记住密码和自动填充

 <template>
  <div
    class="el-password el-input"
    :class="[size ? 'el-input--' + size : '', { 'is-disabled': disabled }]"
  >
    <input
      class="el-input__inner"
      :placeholder="placeholder"
      ref="input"
      :style="{ paddingRight: padding + 'px' }"
      :disabled="disabled"
      :readonly="readonly"
      @focus="handleFocus"
      @blur="handleBlur"
      @input="handleInput"
      @change="change"
      @compositionstart="handleCompositionStart"
      @compositionend="handleCompositionEnd"
    />
    <div class="tools">
      <i
        v-if="clearable !== false"
        v-show="pwd !== '' && isfocus"
        @mousedown.prevent
        class="el-input__icon el-icon-circle-close el-input__clear"
        @click="clearValue"
      ></i>
      <i
        v-if="showPassword !== false"
        v-show="pwd !== '' || isfocus"
        class="el-input__icon el-icon-view el-input__clear"
        @click="changePasswordShow"
      ></i>
    </div>
  </div>
</template> 


<script>
import emitter from "element-ui/src/mixins/emitter";
//自定义密码输入框//input元素光标操作
class CursorPosition {
  constructor(_inputEl) {
    this._inputEl = _inputEl;
  }
  //获取光标的位置 前,后,以及中间字符
  get() {
    var rangeData = { text: "", start: 0, end: 0 };
    if (this._inputEl.setSelectionRange) {
      // W3C
      this._inputEl.focus();
      rangeData.start = this._inputEl.selectionStart;
      rangeData.end = this._inputEl.selectionEnd;
      rangeData.text =
        rangeData.start != rangeData.end
          ? this._inputEl.value.substring(rangeData.start, rangeData.end)
          : "";
    } else if (document.selection) {
      // IE
      this._inputEl.focus();
      var i,
        oS = document.selection.createRange(),
        oR = document.body.createTextRange();
      oR.moveToElementText(this._inputEl);
      rangeData.text = oS.text;
      rangeData.bookmark = oS.getBookmark();
      for (
        i = 0;
        oR.compareEndPoints("StartToStart", oS) < 0 &&
        oS.moveStart("character", -1) !== 0;
        i++
      ) {
        if (this._inputEl.value.charAt(i) == "\r") {
          i++;
        }
      }
      rangeData.start = i;
      rangeData.end = rangeData.text.length + rangeData.start;
    }
    return rangeData;
  }
  //写入光标的位置
  set(rangeData) {
    var oR;
    if (!rangeData) {
      console.warn("You must get cursor position first.");
    }
    this._inputEl.focus();
    if (this._inputEl.setSelectionRange) {
      //  W3C
      this._inputEl.setSelectionRange(rangeData.start, rangeData.end);
    } else if (this._inputEl.createTextRange) {
      // IE
      oR = this._inputEl.createTextRange();
      if (this._inputEl.value.length === rangeData.start) {
        oR.collapse(false);
        oR.select();
      } else {
        oR.moveToBookmark(rangeData.bookmark);
        oR.select();
      }
    }
  }
}
export default {
  name: "el-password",
  props: {
    value: { default: "" },
    size: { type: String, default: "" },
    placeholder: { type: String, default: "请输入" },
    disabled: { type: [Boolean, String], default: false },
    readonly: { type: [Boolean, String], default: false },
    clearable: { type: [Boolean, String], default: false },
    showPassword: { type: [Boolean, String], default: false },
  },
  data() {
    return {
      symbol: "●", //自定义的密码符号
      pwd: "", //密码明文数据
      padding: 15,
      show: false,
      isfocus: false,
      inputEl: null, //input元素
      isComposing: false, //输入框是否还在输入(记录输入框输入的是虚拟文本还是已确定文本)
    };
  },
  mounted() {
    this.inputEl = this.$refs.input;
    this.pwd = this.value;
    this.inputDataConversion(this.pwd);
  },
  mixins: [emitter],
  watch: {
    value: {
      handler: function (value) {
        if (this.inputEl) {
          this.pwd = value;
          this.inputDataConversion(this.pwd);
        }
      },
    },
    showPassword: {
      handler: function (value) {
        let padding = 15;
        if (value) {
          padding += 18;
        }
        if (this.clearable) {
          padding += 18;
        }
        this.padding = padding;
      },
      immediate: true,
    },
    clearable: {
      handler: function (value) {
        let padding = 15;
        if (value) {
          padding += 18;
        }
        if (this.showPassword) {
          padding += 18;
        }
        this.padding = padding;
      },
      immediate: true,
    },
  },
  methods: {
    select() {
      this.$refs.input.select();
    },
    focus() {
      this.$refs.input.focus();
    },
    blur() {
      this.$refs.input.blur();
    },
    handleFocus(event) {
      this.isfocus = true;
      this.$emit("focus", event);
    },
    handleBlur(event) {
      this.isfocus = false;
      this.$emit("blur", event);
      //校验表单
      this.dispatch("ElFormItem", "el.form.blur", [this.value]);
    },
    change(...args) {
      this.$emit("change", ...args);
    },
    clearValue() {
      this.pwd = "";
      this.inputEl.value = "";
      this.$emit("input", "");
      this.$emit("change", "");
      this.$emit("clear");
      this.$refs.input.focus();
    },
    changePasswordShow() {
      this.show = !this.show;
      this.inputDataConversion(this.pwd);
      this.$refs.input.focus();
    },
    inputDataConversion(value) {
      //输入框里的数据转换,将123转为●●●
      if (!value) {
        this.inputEl.value = "";
        return;
      }
      let data = "";
      for (let i = 0; i < value.length; i++) {
        data += this.symbol;
      }
      //使用元素的dataset属性来存储和访问自定义数据-*属性 (存储转换前数据)
      this.inputEl.dataset.value=  this.pwd;
      this.inputEl.value = this.show ? this.pwd : data;
    },
    pwdSetData(positionIndex, value) {
      //写入原始数据
      let _pwd = value.split(this.symbol).join("");
      if (_pwd) {
        let index = this.pwd.length - (value.length - positionIndex.end);
        this.pwd =
          this.pwd.slice(0, positionIndex.end - _pwd.length) +
          _pwd +
          this.pwd.slice(index);
      } else {
        this.pwd =
          this.pwd.slice(0, positionIndex.end) +
          this.pwd.slice(positionIndex.end + this.pwd.length - value.length);
      }
    },
    handleInput(e) {
      //输入值变化后执行 //撰写期间不应发出输入
      if (this.isComposing) return;
      let cursorPosition = new CursorPosition(this.inputEl);
      let positionIndex = cursorPosition.get();
      let value = e.target.value;
      //整个输入框的值
      if (this.show) {
        this.pwd = value;
      } else {
        this.pwdSetData(positionIndex, value);
        this.inputDataConversion(value);
      }
      cursorPosition.set(positionIndex, this.inputEl);
      this.$emit("input", this.pwd);
    },
    handleCompositionStart() {
      //表示正在写
      this.isComposing = true;
    },
    handleCompositionEnd(e) {
      if (this.isComposing) {
        this.isComposing = false;
        //handleCompositionEnd比handleInput后执行,避免isComposing还为true时handleInput无法执行正确逻辑
        this.handleInput(e);
      }
    },
  },
};
</script>

<style scoped>
.tools {
  position: absolute;
  right: 5px;
  display: flex;
  align-items: center;
  top: 0;
  height: 100%;
  z-index: 1;
}
</style>

引用组件

<template>
  <div>
    <el-form
      style="width: 320px; margin: 50px auto"
      :model="fromData"
      ref="elfrom"
      :rules="rules"
    >
      <el-form-item label="密码" prop="password">
        <el-password
          size="small"
          v-model="fromData.password"
          show-password
          placeholder="请输入密码"
        >
        </el-password>
      </el-form-item>
      <el-form-item label="确认密码" prop="confirmPassword">
        <el-password
          size="small"
          v-model="fromData.confirmPassword"
          show-password
          placeholder="请再次输入密码"
        >
        </el-password>
      </el-form-item>
    </el-form>
    <br />
  </div>
</template>
<script>
import elPassword from "./el-password.vue";
export default {
  data() {
    return {
      fromData: {
        password: "",
        confirmPassword: "",
      },
      rules: {
        password: [
          {
            required: true,
            validator: (rule, value, callback) => {
              if (!value) {
                callback(new Error("请输入密码"));
              } else if (
                /^(?=.*[a-zA-Z])(?=.*\d)(?=.*[^a-zA-Z0-9]).{10,20}$/.test(
                  value
                ) === true
              ) {
                callback();
              } else {
                callback(
                  new Error("密码范围在10~20位之间!须包含字母数字特殊符号")
                );
              }
            },
            trigger: "blur",
          },
        ],
        confirmPassword: [
          {
            required: true,
            validator: (rule, value, callback) => {
              if (!value) {
                callback(new Error("请输入确认密码"));
              } else if (value != this.fromData.password) {
                callback(new Error("二次密码不一致"));
              } else {
                callback();
              }
            },
            trigger: "blur",
          },
        ],
      },
    };
  },
  components: {
    elPassword,
  },
};
</script>
        
 
        
 

效果图

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1342270.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

ssm基于JAVA的学生在线考试系统+vue论文

摘 要 如今社会上各行各业&#xff0c;都喜欢用自己行业的专属软件工作&#xff0c;互联网发展到这个时候&#xff0c;人们已经发现离不开了互联网。新技术的产生&#xff0c;往往能解决一些老技术的弊端问题。因为传统考试信息管理难度大&#xff0c;容错率低&#xff0c;管理…

目标检测-One Stage-SSD

文章目录 前言一、SSD的网络结构和流程二、SSD的创新点总结 前言 根据前文目标检测-Two Stage-YOLOv1可以看出YOLOv1的主要缺点是&#xff1a; 每个格子针对目标框的回归是不加限制的&#xff0c;导致目标的定位并不是很精准和Faster RCNN等先进Two Stage算法相比&#xff0c…

1.DQL查询数据(超重点)以及distinct(去重)

DQL(Data Query Language:数据查询语言) 1.所有查询操作都用 SELECT 2.无论是简单的查询还是复杂的查询它都能做 3.数据库中最核心的语言&#xff0c;最重要的语句 4.使用频率最高的语句 语法&#xff1a; SELECT 字段1&#xff0c;字段2&#xff0c;……FROM 表 有时候…

GitHub教程-自定义个人页制作

GitHub是全球最大的代码托管平台&#xff0c;除了存放代码&#xff0c;它还允许用户个性化定制自己的主页&#xff0c;展示个人特色、技能和项目。本教程旨在向GitHub用户展示如何制作个性化主页&#xff0c;同时&#xff0c;介绍了GitHub Actions的应用&#xff0c;可以自动化…

2023-12-29 工作心得补充 适时抽取方法,让代码变简洁

1 JSONObject 实际上是个map 2 数据库实际上也是map 只不过map 是竖着写&#xff0c;数据库横着写. 3 像 用户名 密码 这种后续可能随时会改的&#xff0c;不要写死在代码里&#xff0c;都写成nacos参数。 4 方法的抽取 让代码变得简洁 可读性很高。这是方法抽取的秘诀。写文…

力扣题目学习笔记(OC + Swift)25. K 个一组翻转链表

K 个一组翻转链表 给你链表的头节点 head &#xff0c;每 k 个节点一组进行翻转&#xff0c;请你返回修改后的链表。 k 是一个正整数&#xff0c;它的值小于或等于链表的长度。如果节点总数不是 k 的整数倍&#xff0c;那么请将最后剩余的节点保持原有顺序。 你不能只是单纯的改…

2024年U.S.News全美最佳大学排名公布(附top100榜单)

9月18日&#xff0c;《美国新闻与世界报道》正式发布了最新的2024全美最佳综合大学排名。知识人网小编整理并附上top100的学校榜单&#xff0c;以供访问学者、博士后及联合培养博士们参考。 2024 US News 排名机制调整 U.S. News的排名综合考虑了包括录取率、师生比例、学生标…

大创项目推荐 深度学习中文汉字识别

文章目录 0 前言1 数据集合2 网络构建3 模型训练4 模型性能评估5 文字预测6 最后 0 前言 &#x1f525; 优质竞赛项目系列&#xff0c;今天要分享的是 &#x1f6a9; 深度学习中文汉字识别 该项目较为新颖&#xff0c;适合作为竞赛课题方向&#xff0c;学长非常推荐&#xf…

Qt Designer中各个模块的详细介绍,小白一看就会!!第一部分——layouts模块与Spacers模块

Qt Designer 第一部分&#xff1a;layouts介绍第二部分&#xff1a;Spacers介绍总结&#xff08;非小白可忽略&#xff09; 第一部分&#xff1a;layouts介绍 Qt Designer中的layouts模块提供了多种布局方式&#xff0c;包括垂直布局、水平布局、网格布局和表单布局。这些布局…

音画欣赏|《河水不犯井水的游戏》

《河水不犯井水的游戏》 尺寸&#xff1a;130x90cm 陈可之2007年绘 《警示贤文》之人和篇 天时不如地利&#xff0c;地利不如人和。 黄金未为贵&#xff0c;安乐值钱多。 钱财如粪土&#xff0c;仁义值千斤。 两人一般心&#xff0c;有钱堪买金。 一人一般心&#xff0c;无…

HTML+CSS+JS网页设计期末课程大作业 web课程设计 web前端开发 网页规划与设计

HTMLCSSJS网页设计期末课程大作业 web前端开发技术 web课程设计 网页规划与设计 &#x1f4a5; 文章目录一、&#x1f6a9; 网站描述二、&#x1f38c; 网站介绍三、&#x1f3f4; 网站类型A 个人博客主题B 人物明星主题C 旅游主题D 游戏主题E 动漫主题F 美食主题G 校园主题H 企…

记一次修复外网无法访问vmware里面的虚拟机的网络端口的问题

发现一个奇怪的网络问题&#xff0c;vmware里一个程序的端口通过vmnat穿透出来&#xff0c;然后这个端口就能够通过局域网被其他机器访问&#xff0c;但是另一个网段就没法访问这个端口。使用主机上的其他程序使用开启同样的端口&#xff0c;另一个网段的机器却可以访问。我想不…

探索 EndNote:卓越文献管理工具的功能与应用

引言 在当今科研与学术写作的领域&#xff0c;文献管理是每一位研究者都不可避免面对的挑战。为了有效地整理、引用和协作&#xff0c;研究者需要强大而灵活的文献管理工具。EndNote作为一款备受推崇的文献管理软件&#xff0c;在解决这一问题上发挥着关键作用。本文将深入探讨…

OpenCV-Python(21):轮廓层次结构

目标 学习轮廓的层次结构&#xff0c;了解轮廓之间的父子关系 原理 在前面的内容中我们使用函数cv2.findContours() 来查找轮廓的时候&#xff0c;我们会传入一个参数:轮廓提取模式&#xff08;Contour_Retrieval_Mode&#xff09;。我们总是把它&#x10456d;置为cv2.RETR_…

css+js实现鼠标移动边框高亮效果

前言&#xff1a;效果是鼠标移入空白区域&#xff0c;边框高亮的效果。效果是在douyin的渡一教育袁老师的课程学习到的&#xff0c;观看以后是一个实用的小特效。想看的可以平台查询&#xff0c;自己也学到了知识。 <!DOCTYPE html> <html lang"en"> <…

Erlang、RabbitMQ下载与安装教程(windows超详细)

目录 安装Erlang 1.首先安装RabbitMQ需要安装Erlang环境 2.点击下载好的.exe文件进行傻瓜式安装,一直next即可 3.配置Erlang环境变量 安装RabbitMQ 1.给出RabbitMQ官网下载址&#xff1a;Installing on Windows — RabbitMQ&#xff0c;找到 2.配置RabbitMQ环境变量&#xff0…

3. Bean 的配置

配置信息的继承 查看下面两个 Employee 的配置&#xff0c;其中 dept 属性是重复的: <bean id"dept" class"com.parent.bean.Department"><property name"deptId" value"100"/><property name"deptName" v…

#define定义宏

#define的定义范围 #define不光可以定义变量&#xff0c;常量&#xff0c;还可以定义几乎所有的东西&#xff0c;因为#define可以定义一串代码&#xff08;即宏&#xff09;&#xff0c;所以包含在代码中的东西都能被定义。 #define定义宏 定义是宏名必须于它的参数括号紧挨&am…

秋招复习篇之代码规范

目录 前言 1、变量命名 2、代码空格 1&#xff09;操作符左右一定有空格&#xff0c; 2&#xff09;分隔符&#xff08;, 和;&#xff09;前一位没有空格&#xff0c;后一位保持空格&#xff0c;例如&#xff1a; 3&#xff09;大括号和函数保持同一行&#xff0c;并有一个空格…

2024年第三届服务机器人国际会议(ICoSR 2024) | Ei、Scopus双检索

会议简介 Brief Introduction 2024年第三届服务机器人国际会议(ICoSR 2024) 会议时间&#xff1a;2024年7月26日-28日 召开地点&#xff1a;中国杭州 大会官网&#xff1a;www.iwosr.org 进入新时代&#xff0c;科技更新迭代快速发展&#xff0c;机器人不仅变得更加节能&#x…