Filter features by multiple attributes using checkbox?

2658
6
Jump to solution
02-14-2021 10:55 PM
ZenBahsin
New Contributor II

Hallo, im newbie about arcgis api js, i want to question, how to filter by multiple attributes using checkbox, in below im to try use this code, 

but this my code, just filter by one filter, i want to filter by multiple atributes and show on map, example when i checkbox ACEH and SUMATERA UTARA i want to filter by ACEH and SUMATERA BARAT and show it together on map by checkbox input.

this is my code, Thanks Before.

https://codepen.io/zenbahsin/pen/vYyxLNW?editors=1000 

 

 

<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Filter features by attribute | Sample | ArcGIS API for JavaScript 4.18</title>

  <link rel="stylesheet" href="https://js.arcgis.com/4.18/esri/themes/light/main.css" />
  <script src="https://js.arcgis.com/4.18/"></script>

  <style>
    html,
    body,
    #viewDiv {
      padding: 0;
      margin: 0;
      height: 100%;
      width: 100%;
    }

    #seasons-filter {
      height: 100px;
      width: 180px;
      visibility: hidden;
    }

    .season-item {
      width: 100%;
      padding: 12px;
      text-align: center;
      vertical-align: baseline;
      cursor: pointer;
      height: 50px;
    }

    .season-item:focus {
      background-color: dimgrey;
    }

    .season-item:hover {
      background-color: dimgrey;
    }

    #titleDiv {
      padding: 10px;
    }

    #titleText {
      font-size: 20pt;
      font-weight: 60;
      padding-bottom: 10px;
    }

  </style>
  <script>
    require([
      "esri/views/MapView",
      "esri/Map",
      "esri/layers/FeatureLayer",
      "esri/widgets/Expand"
    ], function (
      MapView, Map, FeatureLayer, Expand
    ) {
      let floodLayerView;

    
      const layer = new FeatureLayer({
          url:
            "https://gis.dukcapil.kemendagri.go.id/arcgis/rest/services/Usia_Produktif_2020_Prov/MapServer/0",

          outFields: ["*"]
        });

      const map = new Map({
        basemap: "gray-vector",
        layers: [layer]
      });

      const view = new MapView({
        map: map,
        container: "viewDiv",
        center: [116.6333769, -0.6171669],
       zoom: 3,
      });

      const seasonsNodes = document.querySelectorAll(`.season-item`);
      const seasonsElement = document.getElementById("seasons-filter");

      // click event handler for seasons choices
      seasonsElement.addEventListener("click", filterBySeason);

      // User clicked on Winter, Spring, Summer or Fall
      // set an attribute filter on flood warnings layer view
      // to display the warnings issued in that season
      function filterBySeason(event) {
        const selectedSeason = event.target.getAttribute("data-season");
        floodLayerView.filter = {
          where: "provinsi = '" + selectedSeason + "'"
        };
      }

      view.whenLayerView(layer).then(function (layerView) {
        // flash flood warnings layer loaded
        // get a reference to the flood warnings layerview
        floodLayerView = layerView;

        // set up UI items
        seasonsElement.style.visibility = "visible";
        const seasonsExpand = new Expand({
          view: view,
          content: seasonsElement,
          expandIconClass: "esri-icon-filter",
          group: "top-left"
        });
        //clear the filters when user closes the expand widget
        seasonsExpand.watch("expanded", function () {
          if (!seasonsExpand.expanded) {
            floodLayerView.filter = null;
          }
        });
        view.ui.add(seasonsExpand, "top-left");
        view.ui.add("titleDiv", "top-right");
      });
    });

  </script>
</head>

<body>
  <div id="seasons-filter" class="esri-widget">
    

     
  <div class="form-check">
  <input type="checkbox" value="1" id="flexCheckDefault" name="selectAceh[]" data-season="ACEH">
  <label class="form-check-label" for="flexCheckDefault">
    ACEH
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="1" id="flexCheckDefault" name="selectSumut[]" data-season="SUMATERA UTARA">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA UTARA
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="1" id="flexCheckDefault" name="selectSumbar[]" data-season="SUMATERA BARAT">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA BARAT
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="1" id="flexCheckDefault" name="selectSumsel[]" data-season="SUMATERA SELATAN">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA SELATAN
  </label>
  </div>

  </div>
  <div id="viewDiv"></div>
</body>

</html>

 

 

 

0 Kudos
1 Solution

Accepted Solutions
PanagiotisPapadopoulos
Esri Regular Contributor
<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Filter features by attribute | Sample | ArcGIS API for JavaScript 4.18</title>

  <link rel="stylesheet" href="https://js.arcgis.com/4.18/esri/themes/light/main.css" />
  <script src="https://js.arcgis.com/4.18/"></script>

  <style>
    html,
    body,
    #viewDiv {
      padding0;
      margin0;
      height100%;
      width100%;
    }

    #seasons-filter {
      height100px;
      width180px;
      visibilityhidden;
    }

    .season-item {
      width100%;
      padding12px;
      text-aligncenter;
      vertical-alignbaseline;
      cursorpointer;
      height50px;
    }

    .season-item:focus {
      background-colordimgrey;
    }

    .season-item:hover {
      background-colordimgrey;
    }

    #titleDiv {
      padding10px;
    }

    #titleText {
      font-size20pt;
      font-weight60;
      padding-bottom10px;
    }

  </style>
  <script>
    require([
      "esri/views/MapView",
      "esri/Map",
      "esri/layers/FeatureLayer",
      "esri/widgets/Expand"
    ], function (
      MapViewMapFeatureLayerExpand
    ) {
      let floodLayerView;

    
      const layer = new FeatureLayer({
          url:

          outFields: ["*"]
        });

      const map = new Map({
        basemap: "gray-vector",
        layers: [layer]
      });

      const view = new MapView({
        map: map,
        container: "viewDiv",
        center: [116.6333769, -0.6171669],
       zoom: 3,
      });

      const seasonsNodes = document.querySelectorAll(`.season-item`);
      const seasonsElement = document.getElementById("seasons-filter");

      // click event handler for seasons choices
      seasonsElement.addEventListener("click"filterBySeason);

      // User clicked on Winter, Spring, Summer or Fall
      // set an attribute filter on flood warnings layer view
      // to display the warnings issued in that season
      function filterBySeason(event) {
        const selectedSeason = event.target.getAttribute("data-season");
        
          var markedCheckbox = document.getElementsByClassName('checkboxCL');  
          var queryWhere=[];
          for (var checkbox of markedCheckbox) {  
            if (checkbox.checked)  
              queryWhere.push("'"+checkbox.value+"'");  
          }  
        floodLayerView.filter = {
          where: "provinsi in(" + queryWhere.toString() + ")"
        };
        alert("provinsi  in(" + queryWhere.toString() + ")");
      }

      view.whenLayerView(layer).then(function (layerView) {
        // flash flood warnings layer loaded
        // get a reference to the flood warnings layerview
        floodLayerView = layerView;

        // set up UI items
        seasonsElement.style.visibility = "visible";
        const seasonsExpand = new Expand({
          view: view,
          content: seasonsElement,
          expandIconClass: "esri-icon-filter",
          group: "top-left"
        });
        //clear the filters when user closes the expand widget
        seasonsExpand.watch("expanded"function () {
          if (!seasonsExpand.expanded) {
            floodLayerView.filter = null;
          }
        });
        view.ui.add(seasonsExpand"top-left");
        view.ui.add("titleDiv""top-right");
      });
    });

  </script>
</head>

<body>
  <div id="seasons-filter" class="esri-widget">
    

     
  <div class="form-check">
  <input type="checkbox" value="ACEH" class="checkboxCL" id="flexCheckDefault" name="selectAceh[]" data-season="ACEH">
  <label class="form-check-label" for="flexCheckDefault">
    ACEH
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="SUMATERA UTARA" class="checkboxCL" id="flexCheckDefault" name="selectSumut[]" data-season="SUMATERA UTARA">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA UTARA
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="SUMATERA BARAT" class="checkboxCL" id="flexCheckDefault" name="selectSumbar[]" data-season="SUMATERA BARAT">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA BARAT
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="SUMATERA SELATAN" class="checkboxCL" id="flexCheckDefault" name="selectSumsel[]" data-season="SUMATERA SELATAN">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA SELATAN
  </label>
  </div>

  </div>
  <div id="viewDiv"></div>
</body>

</html>

View solution in original post

6 Replies
PanagiotisPapadopoulos
Esri Regular Contributor
<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Filter features by attribute | Sample | ArcGIS API for JavaScript 4.18</title>

  <link rel="stylesheet" href="https://js.arcgis.com/4.18/esri/themes/light/main.css" />
  <script src="https://js.arcgis.com/4.18/"></script>

  <style>
    html,
    body,
    #viewDiv {
      padding0;
      margin0;
      height100%;
      width100%;
    }

    #seasons-filter {
      height100px;
      width180px;
      visibilityhidden;
    }

    .season-item {
      width100%;
      padding12px;
      text-aligncenter;
      vertical-alignbaseline;
      cursorpointer;
      height50px;
    }

    .season-item:focus {
      background-colordimgrey;
    }

    .season-item:hover {
      background-colordimgrey;
    }

    #titleDiv {
      padding10px;
    }

    #titleText {
      font-size20pt;
      font-weight60;
      padding-bottom10px;
    }

  </style>
  <script>
    require([
      "esri/views/MapView",
      "esri/Map",
      "esri/layers/FeatureLayer",
      "esri/widgets/Expand"
    ], function (
      MapViewMapFeatureLayerExpand
    ) {
      let floodLayerView;

    
      const layer = new FeatureLayer({
          url:

          outFields: ["*"]
        });

      const map = new Map({
        basemap: "gray-vector",
        layers: [layer]
      });

      const view = new MapView({
        map: map,
        container: "viewDiv",
        center: [116.6333769, -0.6171669],
       zoom: 3,
      });

      const seasonsNodes = document.querySelectorAll(`.season-item`);
      const seasonsElement = document.getElementById("seasons-filter");

      // click event handler for seasons choices
      seasonsElement.addEventListener("click"filterBySeason);

      // User clicked on Winter, Spring, Summer or Fall
      // set an attribute filter on flood warnings layer view
      // to display the warnings issued in that season
      function filterBySeason(event) {
        const selectedSeason = event.target.getAttribute("data-season");
        
          var markedCheckbox = document.getElementsByClassName('checkboxCL');  
          var queryWhere=[];
          for (var checkbox of markedCheckbox) {  
            if (checkbox.checked)  
              queryWhere.push("'"+checkbox.value+"'");  
          }  
        floodLayerView.filter = {
          where: "provinsi in(" + queryWhere.toString() + ")"
        };
        alert("provinsi  in(" + queryWhere.toString() + ")");
      }

      view.whenLayerView(layer).then(function (layerView) {
        // flash flood warnings layer loaded
        // get a reference to the flood warnings layerview
        floodLayerView = layerView;

        // set up UI items
        seasonsElement.style.visibility = "visible";
        const seasonsExpand = new Expand({
          view: view,
          content: seasonsElement,
          expandIconClass: "esri-icon-filter",
          group: "top-left"
        });
        //clear the filters when user closes the expand widget
        seasonsExpand.watch("expanded"function () {
          if (!seasonsExpand.expanded) {
            floodLayerView.filter = null;
          }
        });
        view.ui.add(seasonsExpand"top-left");
        view.ui.add("titleDiv""top-right");
      });
    });

  </script>
</head>

<body>
  <div id="seasons-filter" class="esri-widget">
    

     
  <div class="form-check">
  <input type="checkbox" value="ACEH" class="checkboxCL" id="flexCheckDefault" name="selectAceh[]" data-season="ACEH">
  <label class="form-check-label" for="flexCheckDefault">
    ACEH
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="SUMATERA UTARA" class="checkboxCL" id="flexCheckDefault" name="selectSumut[]" data-season="SUMATERA UTARA">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA UTARA
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="SUMATERA BARAT" class="checkboxCL" id="flexCheckDefault" name="selectSumbar[]" data-season="SUMATERA BARAT">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA BARAT
  </label>
  </div>
  
   <div class="form-check">
  <input type="checkbox" value="SUMATERA SELATAN" class="checkboxCL" id="flexCheckDefault" name="selectSumsel[]" data-season="SUMATERA SELATAN">
  <label class="form-check-label" for="flexCheckDefault">
   SUMATERA SELATAN
  </label>
  </div>

  </div>
  <div id="viewDiv"></div>
</body>

</html>
PanagiotisPapadopoulos
Esri Regular Contributor

Hi I changed the following function

  function filterBySeason(event) {
        const selectedSeason = event.target.getAttribute("data-season");
        
          var markedCheckbox = document.getElementsByClassName('checkboxCL');  
          var queryWhere=[];
          for (var checkbox of markedCheckbox) {  
            if (checkbox.checked)  
              queryWhere.push("'"+checkbox.value+"'");  
          }  
        floodLayerView.filter = {
          where: "provinsi in(" + queryWhere.toString() + ")"
        };
        alert("provinsi = in(" + queryWhere.toString() + ")");
      }
 
and the check boxes
 
<input type="checkbox" value="SUMATERA BARAT" class="checkboxCL" id="flexCheckDefault" name="selectSumbar[]" data-season="SUMATERA BARAT">
 
The idea is to parse all the check boxes and get the values from the selected. Then create a where clause including all the selected values. 
 
ZenBahsin
New Contributor II

Thank you so much sir, you save my life

0 Kudos
ZenBahsin
New Contributor II

 Sorry I asked again, how do I uncheck the checkbox when expand is turned off?

0 Kudos
PanagiotisPapadopoulos
Esri Regular Contributor

what did you mean when you say the expand is turned off? 

ZenBahsin
New Contributor II

I mean checkbox.checked is false when !seasonsExpand.expanded

but i have resolved this problem, i  have added the following line of code like bellow

  seasonsExpand.watch("expanded", function () {
          if (!seasonsExpand.expanded) {
            
            floodLayerView.filter = false;
            // checkbox.checked = false;
             var markedCheckbox = document.getElementsByClassName('checkboxCL');  
            for (var checkbox of markedCheckbox) {
              if (checkbox.checked){
                checkbox.checked = false;
              }
            }             
          }
        });
0 Kudos