点击查看html编辑器说明文档

验证码,校验码设计edit icon

|
|
Fork(复制)
|
|
作者:
lynn-ssk
提交反馈
嵌入
设置
下载
HTML
格式化
支持Emmet,输入 p 后按 Tab键试试吧!
<head> ...
展开
</head>
<body>
            
            <section>
  <div class="container">
    <h1 class="title">输入验证码</h1>
    <form id="otp-form">
      <input type="text" class="otp-input" maxlength="1">
      <input type="text" class="otp-input" maxlength="1">
      <input type="text" class="otp-input" maxlength="1">
      <input type="text" class="otp-input" maxlength="1">
      <input type="text" class="otp-input" maxlength="1">
    </form>
    <button id="verify-btn">点击验证</button>
  </div>
</section>
        
</body>
CSS
格式化
            
            @import url("https://fonts.googleapis.com/css2?family=Inter&display=swap");
* {
  padding: 0;
  margin: 0;
  box-sizing: border-box;
  font-family: Inter;
}
body {
  width: 100%;
  background: #1a2226;
  color: white;
}
section {
  width: 100%;
  min-height: 100vh;
  display: flex;
  align-items: center;
  justify-content: center;
  flex-direction: column;
}
.container {
  border-radius: 12px;
  background-color: rgb(19, 25, 28);
  width: 90%;
  max-width: 500px;
  padding: 50px 20px;
  text-align: center;
}
.title {
  font-size: 25px;
  margin-bottom: 30px;
}
#otp-form {
  width: 100%;
  display: flex;
  gap: 20px;
  align-items: center;
  justify-content: center;
}
#otp-form input {
  border: none;
  background-color: #121517;
  color: white;
  font-size: 32px;
  text-align: center;
  padding: 10px;
  width: 100%;
  max-width: 70px;
  height: 70px;
  border-radius: 4px;
  outline: 2px solid rgb(66, 66, 66);
}
#otp-form input:focus-visible {
  outline: 2px solid royalblue;
}
#otp-form input.filled {
  outline: 2px solid rgb(7, 192, 99);
}
#verify-btn {
  cursor: pointer;
  display: inline-block;
  margin-top: 30px;
  background: royalblue;
  color: white;
  padding: 7px 10px;
  border-radius: 4px;
  font-size: 16px;
  border: none;
}

        
JS
格式化
            
            const form = document.querySelector("#otp-form");
const inputs = document.querySelectorAll(".otp-input");
const verifyBtn = document.querySelector("#verify-btn");

const isAllInputFilled = () => {
  return Array.from(inputs).every((item) => item.value);
};

const getOtpText = () => {
  let text = "";
  inputs.forEach((input) => {
    text += input.value;
  });
  return text;
};

const verifyOTP = () => {
  if (isAllInputFilled()) {
    const text = getOtpText();
    alert(`Your OTP is "${text}". OTP is correct`);
  }
};

const toggleFilledClass = (field) => {
  if (field.value) {
    field.classList.add("filled");
  } else {
    field.classList.remove("filled");
  }
};

form.addEventListener("input", (e) => {
  const target = e.target;
  const value = target.value;
  console.log({ target, value });
  toggleFilledClass(target);
  if (target.nextElementSibling) {
    target.nextElementSibling.focus();
  }
  verifyOTP();
});

inputs.forEach((input, currentIndex) => {
  // fill check
  toggleFilledClass(input);

  // paste event
  input.addEventListener("paste", (e) => {
    e.preventDefault();
    const text = e.clipboardData.getData("text");
    console.log(text);
    inputs.forEach((item, index) => {
      if (index >= currentIndex && text[index - currentIndex]) {
        item.focus();
        item.value = text[index - currentIndex] || "";
        toggleFilledClass(item);
        verifyOTP();
      }
    });
  });

  // backspace event
  input.addEventListener("keydown", (e) => {
    if (e.keyCode === 8) {
      e.preventDefault();
      input.value = "";
      // console.log(input.value);
      toggleFilledClass(input);
      if (input.previousElementSibling) {
        input.previousElementSibling.focus();
      }
    } else {
      if (input.value && input.nextElementSibling) {
        input.nextElementSibling.focus();
      }
    }
  });
});

verifyBtn.addEventListener("click", () => {
  verifyOTP();
});

        
预览
控制台
清空