【问题标题】:appendChild content doesn't stay even when if condition has been met即使满足条件,appendChild 内容也不会保留
【发布时间】:2022-11-01 23:58:45
【问题描述】:

我正在使用 javascript 检查表单中的必填字段,以便为字段设置样式,如果 focusout 上的字段为空,则会显示错误消息。 (这是对仅在提交时进行验证的 Kirby CMS 表单插件的补充。)

我试图创造的行为是......

  • 当必填字段留空时,focusout 上会显示样式和消息。
  • 样式和消息保持可见,直到 (a) 字段再次处于焦点状态或 (b) 填充字段。
  • 如果必填字段“重新聚焦”,留空并再次聚焦,则消息和样式会重新出现。

我的问题是输入样式(红色边框底部)按预期工作,但基于appendChild 函数的错误消息却没有。错误消息一次只出现一个,其中最后一个重点是必填字段,我不知道如何让消息以与样式相同的方式保持在原位。

因为在实践中,表单将由内容管理员使用 CMS 创建,所以我希望脚本是 vanilla JS 并且尽可能通用,避免针对特定 ID。相反,我试图根据required 属性和querySelectorAll 函数来执行此操作。我有一些变量来指定错误消息文本和for 循环来仅针对不符合if 语句标准的“违规”字段。

function reqdCheck() {
  const reqdFields = document.querySelectorAll("main input[required], main textarea[required]");
  const reqdPara = document.createElement("p");
  const reqdText = document.createTextNode("This field is required.");
  reqdPara.appendChild(reqdText);
  
  for (const reqdField of reqdFields) {
    reqdField.addEventListener ("focusout", function() {
        if (reqdField.value == "" || reqdField.value == null) {
        reqdField.style.borderBottom = "1px solid red";
        reqdField.style.boxShadow = "0 1px 0 0 red";
        reqdField.parentNode.appendChild(reqdPara);
      }
      else {
        reqdField.style.borderBottom = "1px solid black";
        reqdField.style.boxShadow = "none";
      }
    })
    reqdField.addEventListener ("focusin", function() {
      if (reqdField.value == "" || reqdField.value == null) {
        reqdField.style.borderBottom = "1px solid orange";
        reqdField.style.boxShadow = "0 1px 0 0 orange";
        reqdField.parentNode.removeChild(reqdPara);
      }
    })
  }
}
reqdCheck()
input:not([type="submit"]),
textarea {
  border: none;
  border-bottom: 1px solid black;
  display: block;
  width: calc(100% - 40px);
}

input:not([type="submit"]):focus,
textarea:focus {
  outline: none;
  border-bottom: 1px solid orange;
  box-shadow: 0 1px 0 0 orange;
}

.field-group {
  margin-bottom: 20px;
}

.field-group p {
  color: red;
  line-height: 1;
  margin: 5px 0 0;
}
<main>
  <form id="a2a64e93-2b60-4ad9-9445-ce61f5852594" action="#">
    <div class="field-group">
      <label for="fname">First name:*</label><br>
      <input type="text" id="fname" name="fname" placeholder="John" required>
    </div>
    <div class="field-group">
      <label for="lname">Last name:</label><br>
      <input type="text" id="lname" name="lname" placeholder="Doe">
    </div>
    <div class="field-group">
      <label for="company">Company:</label><br>
      <input type="text" id="fname" name="company" placeholder="Acme Ltd">
    </div>
    <div class="field-group">
      <label for="email">Email:*</label><br>
      <input type="email" id="email" name="email" placeholder="john@acme.com" required>
     </div>
    <div class="field-group">
      <label for="email">Message:*</label><br>
      <textarea id="message" name="message" placeholder="Message" required></textarea>
    </div>
    <input type="submit" value="Submit">
  </form>
</main>

为了让 appendChild 错误消息按预期保持可见,我缺少什么?有没有更有效的方法来实现我所追求的?谢谢。

【问题讨论】:

    标签: javascript if-statement appendchild


    【解决方案1】:

    发生这种情况的原因是您只创建了一个 p 元素(错误文本)并且您想多次附加它。为了解决这个问题,您应该在 for 循环中添加所有 reqdPara 逻辑。看看这里:

    function reqdCheck() {
      const reqdFields = document.querySelectorAll(
        'main input[required], main textarea[required]'
      );
    
      for (const reqdField of reqdFields) {
        const reqdPara = document.createElement('p');
        const reqdText = document.createTextNode('This field is required.');
    
        reqdPara.appendChild(reqdText);
    
        reqdField.addEventListener('focusout', function () {
          if (reqdField.value === '' || reqdField.value === null) {
            reqdField.style.borderBottom = '1px solid red';
            reqdField.style.boxShadow = '0 1px 0 0 red';
            reqdField.parentNode.appendChild(reqdPara);
          } else {
            reqdField.style.borderBottom = '1px solid black';
            reqdField.style.boxShadow = 'none';
          }
        });
        reqdField.addEventListener('focusin', function () {
          if (reqdField.value == '' || reqdField.value == null) {
            reqdField.style.borderBottom = '1px solid orange';
            reqdField.style.boxShadow = '0 1px 0 0 orange';
            reqdField.parentNode.removeChild(reqdPara);
          }
        });
      }
    }
    reqdCheck();
    

    【讨论】:

    • 谢谢,30分。这正是我所需要的!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-03-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-04-05
    • 2013-04-08
    相关资源
    最近更新 更多