You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

多实例Multiselect Dropdown仅首个下拉框更新问题求助

问题描述

实现的多选下拉框存在异常:选择第二个或其他下拉框的选项时,仅第一个下拉框会更新,其余下拉框完全无响应。

期望效果

从第二个下拉框选择选项(如「Research Report」)时,该下拉框应与第一个一样生成对应的选中标签。

代码实现

JavaScript代码

document.addEventListener("DOMContentLoaded", function() {
  let fieldContainers = document.querySelectorAll(".field");
  fieldContainers.forEach((fieldContainer, index) => {
    let checkbox = fieldContainer.querySelectorAll(`#divOptions input`);
    let inputCheckbox = fieldContainer.querySelector("#inputCheckbox");
    let unorderedList = document.createElement("ul");
    unorderedList.className = "filtertags";

    for (let i = 0; i < checkbox.length; i++) {
      checkbox[i].addEventListener("change", function(e) {
        if (e.target.checked) {
          let liTag = `<li class="txt-16-500">${checkbox[i].value}<i class="remTag"><svg width="10" height="10" viewBox="0 0 10 10" fill="none" xmlns="http://www.w3.org/2000/svg">
                        <path d="M10 1.00714L8.99286 0L5 3.99286L1.00714 0L0 1.00714L3.99286 5L0 8.99286L1.00714 10L5 6.00714L8.99286 10L10 8.99286L6.00714 5L10 1.00714Z" fill="#FEFEFE"/>
                        </svg></i>
                      </li>`;
          unorderedList.insertAdjacentHTML("beforeend", liTag);
          let remIcon = unorderedList.lastElementChild.querySelector(".remTag");
          remIcon.addEventListener("click", function(ev) {
            ev.stopPropagation();
            remIcon.parentElement.remove();
            checkbox[i].checked = false;
            updateInputCheckboxDisplay();
          });
        } else {
          let allLi = unorderedList.querySelectorAll("li");
          allLi.forEach(function(li) {
            if (li.innerText === checkbox[i].value) {
              li.remove();
            }
          });
        }
        updateInputCheckboxDisplay();
      });
    }

    const updateInputCheckboxDisplay = function() {
      inputCheckbox.style.display = unorderedList.childNodes.length > 0 ? "none" : null;
    };

    inputCheckbox.insertAdjacentElement("beforebegin", unorderedList);
  });
});

HTML代码

<form>
  <fieldset>
    <div class="field">
      <p class="txt-14">Status</p>
      <div class="custom-combobox-container">
        <div class="custom-combobox" onclick="showOptions(this)">
          <input type="text" placeholder="Select Status" id="inputCheckbox" readonly />
        </div>
        <div class="options-container" id="divOptions">
          <label class="txt-reg-400" for="one">
            <input type="checkbox" id="one" value="All" /> All
          </label>
          <label class="txt-reg-400" for="two">
            <input type="checkbox" id="two" value="Drafts" />
            Drafts
          </label>
          <label class="txt-reg-400" for="three">
            <input
              type="checkbox"
              id="three"
              value="Approved"
            />
            Approved
          </label>
          <label class="txt-reg-400" for="four">
            <input
              type="checkbox"
              id="four"
              value="Published"
            />
            Published
          </label>
          <label class="txt-reg-400" for="five">
            <input
              type="checkbox"
              id="five"
              value="Submitted"
            />
            Submitted
          </label>
          <label class="txt-reg-400" for="six">
            <input type="checkbox" id="six" value="Updated" />
            Updated
          </label>
          <label class="txt-reg-400" for="seven">
            <input
              type="checkbox"
              id="seven"
              value="Rejected"
            />
            Rejected
          </label>
        </div>
      </div>
    </div>
    <div class="field">
      <p class="txt-14">Document Type</p>
      <div class="custom-combobox-container">
        <div class="custom-combobox" onclick="showOptions(this)">
          <input type="text" placeholder="Select Document Type" id="inputCheckbox" readonly />
        </div>
        <div class="options-container" id="divOptions">
          <label class="txt-reg-400" for="doc1">
            <input type="checkbox" id="doc1" value="Research Report" /> Research Report
          </label>
          <label class="txt-reg-400" for="doc2">
            <input type="checkbox" id="doc2" value="Whitepaper" /> Whitepaper
          </label>
        </div>
      </div>
    </div>
  </fieldset>
</form>

问题原因及修复方案

核心问题

代码中使用了重复的ID(inputCheckbox、divOptions),而DOM规范中ID必须唯一。当通过querySelector或getElementById选择元素时,只会返回第一个匹配的元素,导致后续下拉框的事件绑定全部指向第一个下拉框的元素,所以操作第二个下拉框时只有第一个有反应。

修复步骤

  1. 替换重复ID为类选择器:
    • 将HTML中的id="inputCheckbox"改为class="inputCheckbox"
    • 将id="divOptions"改为class="divOptions"
  2. 修改JavaScript中的选择器逻辑:
    • 把fieldContainer.querySelectorAll(#divOptions input)改为fieldContainer.querySelectorAll(.divOptions input)
    • 把fieldContainer.querySelector("#inputCheckbox")改为fieldContainer.querySelector(".inputCheckbox")

修复后的完整代码

JavaScript代码

document.addEventListener("DOMContentLoaded", function() {
  let fieldContainers = document.querySelectorAll(".field");
  fieldContainers.forEach((fieldContainer, index) => {
    // 改用类选择器获取当前field下的复选框
    let checkbox = fieldContainer.querySelectorAll(`.divOptions input`);
    // 改用类选择器获取当前field下的输入框
    let inputCheckbox = fieldContainer.querySelector(".inputCheckbox");
    let unorderedList = document.createElement("ul");
    unorderedList.className = "filtertags";

    for (let i = 0; i < checkbox.length; i++) {
      checkbox[i].addEventListener("change", function(e) {
        if (e.target.checked) {
          let liTag = `<li class="txt-16-500">${checkbox[i].value}<i class="remTag"><svg width="10" height="10" viewBox="0 0 10 10" fill="none" xmlns="http://www.w3.org/2000/svg">
                        <path d="M10 1.00714L8.99286 0L5 3.99286L1.00714 0L0 1.00714L3.99286 5L0 8.99286L1.00714 10L5 6.00714L8.99286 10L10 8.99286L6.00714 5L10 1.00714Z" fill="#FEFEFE"/>
                        </svg></i>
                      </li>`;
          unorderedList.insertAdjacentHTML("beforeend", liTag);
          let remIcon = unorderedList.lastElementChild.querySelector(".remTag");
          remIcon.addEventListener("click", function(ev) {
            ev.stopPropagation();
            remIcon.parentElement.remove();
            checkbox[i].checked = false;
            updateInputCheckboxDisplay();
          });
        } else {
          let allLi = unorderedList.querySelectorAll("li");
          allLi.forEach(function(li) {
            // 增加trim处理避免空格导致匹配失败
            if (li.innerText.trim() === checkbox[i].value) {
              li.remove();
            }
          });
        }
        updateInputCheckboxDisplay();
      });
    }

    const updateInputCheckboxDisplay = function() {
      inputCheckbox.style.display = unorderedList.childNodes.length > 0 ? "none" : null;
    };

    inputCheckbox.insertAdjacentElement("beforebegin", unorderedList);
  });
});

HTML代码

<form>
  <fieldset>
    <div class="field">
      <p class="txt-14">Status</p>
      <div class="custom-combobox-container">
        <div class="custom-combobox" onclick="showOptions(this)">
          <!-- 替换id为class -->
          <input type="text" placeholder="Select Status" class="inputCheckbox" readonly />
        </div>
        <!-- 替换id为class -->
        <div class="options-container divOptions">
          <label class="txt-reg-400" for="one">
            <input type="checkbox" id="one" value="All" /> All
          </label>
          <label class="txt-reg-400" for="two">
            <input type="checkbox" id="two" value="Drafts" />
            Drafts
          </label>
          <label class="txt-reg-400" for="three">
            <input
              type="checkbox"
              id="three"
              value="Approved"
            />
            Approved
          </label>
          <label class="txt-reg-400" for="four">
            <input
              type="checkbox"
              id="four"
              value="Published"
            />
            Published
          </label>
          <label class="txt-reg-400" for="five">
            <input
              type="checkbox"
              id="five"
              value="Submitted"
            />
            Submitted
          </label>
          <label class="txt-reg-400" for="six">
            <input type="checkbox" id="six" value="Updated" />
            Updated
          </label>
          <label class="txt-reg-400" for="seven">
            <input
              type="checkbox"
              id="seven"
              value="Rejected"
            />
            Rejected
          </label>
        </div>
      </div>
    </div>
    <div class="field">
      <p class="txt-14">Document Type</p>
      <div class="custom-combobox-container">
        <div class="custom-combobox" onclick="showOptions(this)">
          <input type="text" placeholder="Select Document Type" class="inputCheckbox" readonly />
        </div>
        <div class="options-container divOptions">
          <label class="txt-reg-400" for="doc1">
            <input type="checkbox" id="doc1" value="Research Report" /> Research Report
          </label>
          <label class="txt-reg-400" for="doc2">
            <input type="checkbox" id="doc2" value="Whitepaper" /> Whitepaper
          </label>
        </div>
      </div>
    </div>
  </fieldset>
</form>

额外优化建议

  • 确保所有复选框的ID唯一,避免点击标签时触发错误的复选框
  • 保留标签的for属性并与对应复选框ID匹配,保证标签点击的交互正常
  • 匹配标签文本与复选框值时,使用trim()处理,避免因空格导致匹配失败

内容的提问来源于stack exchange,提问作者Harshvardhan Shete

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 20:22:03