首页 > 解决方案 > 如果另一个类的复选框已被选中,如何从 jQuery 过滤器中排除某个复选框类?

问题描述

我是编码新手,不知道自己在做什么。我觉得我也不太擅长解释事情,所以如果这篇文章有点难以理解,我很抱歉。希望查看代码本身更有意义。

基本上,我有一个可以过滤的列表。每个列表项包含多个类。我也有复选框来显示每个单独的类。

但是,有几个类在它们适用的列表项方面重叠,但并不完全相同。

例如,有人要查找 A 类中的内容,但包含 D 类中的内容。如果选中 A 类,它将自动显示 D 类也适用的所有列表项。

我想做的是,如果选中 A 类,您还可以选择从搜索中排除 D 类,以便显示重叠数据。反之亦然(即如果选中 D 类,则可以选择排除 A 类)。

如果可能的话,我也希望这适用于所有课程。这样您就可以检查一个(或多个)类,但同时排除您不感兴趣的某个类,即使列表项重叠(即您已选中 D 类,并且不想要列表项在 B 类中属于 D 类)。

<div class="options">
  <label>
    <input type="radio" name="operation" value="union" id="op-union" checked>Union
  </label>
  <label>
    <input type="radio" name="operation" value="intersection" id="op-inter">Intersection
  </label>
</div>

<div class="categories">
  <span class="category">
    <input type="checkbox" value="classa" id="cat-classa">
    <label for="cat-classa">Class A</label>
  </span>
  <span class="category">
    <input type="checkbox" value="classb" id="cat-classb">
    <label for="cat-classb">Class B</label>
  </span>
  <span class="category">
    <input type="checkbox" value="classc" id="cat-classc">
    <label for="cat-classc">Class C</label>
  </span>
  <span class="category">
    <input type="checkbox" value="classd" id="cat-classd">
    <label for="cat-classd">Class D</label>
  </span>
  <span class="category">
    <input type="checkbox" value="classe" id="cat-classe">
    <label for="cat-classe">Class E</label>
  </span>
  <span class="category">
    <input type="checkbox" value="classf" id="cat-classf">
    <label for="cat-classf">Class F</label>
  </span>
</div>

<div class="container"> 
  <ul>
    <div class="filterDiv classa classd"><li>List 1</li></div>
    <div class="filterDiv classa classe"><li>List 2</li></div>
    <div class="filterDiv classb classd classe"><li>List 3</li></div>
    <div class="filterDiv classc classf">List 4</li></div>
    <div class="filterDiv classb classd classf">List 5</li></div>
  </ul>
</div>

鉴于列表的性质,类和类型的任何组合都是可能的。通常,只有一堂课,但有时有两堂课。在实际列表中,我的一个列表项也不仅仅是三个类。

脚本:

<script>
var checkboxes = document.querySelectorAll(".categories input");
for(var i = 0; i < checkboxes.length; i++) {
  checkboxes[i].addEventListener("change", filter);
}
var radios = document.getElementsByName("operation");
for(var i = 0; i < radios.length; i++) {
  radios[i].addEventListener("change", filter);
}
filter();
function filter() {
  var i, j;

  // Choose an operation
  var operation = document.getElementById("op-union").checked ? "union" : "intersection";

  // Get the selected categories
  var checkboxes = document.querySelectorAll(".categories input");
  var categories = [];
  var c;
  for(i = 0; i < checkboxes.length; i++) {
    if(checkboxes[i].checked) {
      c = checkboxes[i].value;
      categories.push(c);
    }
  }

  // Apply the filter
  var items = document.querySelectorAll(".filterDiv");
  var item, show;
  for(i = 0; i < items.length; i++) {
    item = items[i];
    if(categories.length == 0) {
      show = true;
    } else if(operation == "union") {
      // Union: Only one of the categories needs to exist
      show = false;
      for(j = 0; j < categories.length; j++) {
        if(item.classList.contains(categories[j])) {
          show = true;
          break;
        }
      }
    } else {
      // Intersection: All of the categories must apply
      show = true;
      for(j = 0; j < categories.length; j++) {
        if(!item.classList.contains(categories[j])) {
          show = false;
          break;
        }
      }
    }

    if(show) {
      item.classList.add("show");
    } else {
      item.classList.remove("show");
    }
  }
}
</script>

提前感谢任何帮助的人!我再次为措辞道歉,我对此并不陌生,并且仍在想办法解决这一切。任何尝试都非常感谢。

标签: javascripthtmljquerycheckbox

解决方案


你的代码很好。你需要一些修改。我没有改变你的代码风格,但如果你使用 javascript 更好地使用 let 关键字(现代 javascript)不要再使用 var 并尝试理解减少你的代码的 forEach 循环(除非你正在使用 break 语句)

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
</head>
<body>
  <div class="options">
  <label><input type="radio" name="operation" value="union" id="op-union" checked>A or B</label>
  <label><input type="radio" name="operation" value="intersection" id="op-inter">A and B</label>
</div>

<div class="categories">
<span class="category"><input type="checkbox" value="classa" id="cat-classa"><label for="cat-classa">Class A</label></span>
<span class="category"><input type="checkbox" value="classb" id="cat-classb"><label for="cat-classb">Class B</label></span>
<span class="category"><input type="checkbox" value="classc" id="cat-classc"><label for="cat-classc">Class C</label></span>
<span class="category"><input type="checkbox" value="classd" id="cat-classd"><label for="cat-classd">Class D</label></span>
<span class="category"><input type="checkbox" value="classe" id="cat-classe"><label for="cat-classe">Class E</label></span>
<span class="category"><input type="checkbox" value="classf" id="cat-classf"><label for="cat-classf">Class F</label></span>
</div>

<div class="container"> 
<ul>
<div class="filterDiv classa classd"><li>List 1</li></div>
<div class="filterDiv classa classe"><li>List 2</li></div>
<div class="filterDiv classb classd classe"><li>List 3</li></div>
<div class="filterDiv classc classf">List 4</li></div>
<div class="filterDiv classb classd classf">List 5</li></div>
</ul>
</div>
<script>
  
var checkboxes = document.querySelectorAll(".categories input");
for(var i = 0; i < checkboxes.length; i++) {
  checkboxes[i].addEventListener("change", filter);
}
var radios = document.getElementsByName("operation");
for(var i = 0; i < radios.length; i++) {
  radios[i].addEventListener("change", filter);
}
filter();
function filter() {
  var i, j;

  // Choose an operation
  var operation = document.getElementById("op-union").checked ? "union" : "intersection";

  // Get the selected categories
  var checkboxes = document.querySelectorAll(".categories input");
  var categories = [];
  var c;
  for(i = 0; i < checkboxes.length; i++) {
    if(checkboxes[i].checked) {
      c = checkboxes[i].value;
      categories.push(c);
    }
  }
 

  // Apply the filter
  var items = document.querySelectorAll(".filterDiv");
   items.forEach(item=>item.style.display='block')
  var item, show;
  for(i = 0; i < items.length; i++) {
    item = items[i];
    if(categories.length == 0) {
      show = true;
     
    } else if(operation == "union") {
      // Union: Only one of the categories needs to exist
   
      show = false;
      for(j = 0; j < categories.length; j++) {
        if(item.classList.contains(categories[j])) {
        
          show = true;
          break;
        }
      }
      if(!show){
        item.style.display="none";
      }
    } else {
      //  console.log(operation)
      // Intersection: All of the categories must apply
      show = true;
      for(j = 0; j < categories.length; j++) {
        if(!item.classList.contains(categories[j])) {
          item.style.display="none";
          break;
        }
      }
    }

    // if(show) {
    //   item.classList.add("show");
    // } else {
    //   item.classList.remove("show");
    // }
  }
}


</script>
</body>
</html>


推荐阅读