Search code examples
javascriptarcgisarcgis-js-api

ArcGIS 4.8 JS: State is not showing selected when hover or click


I'm using ArcGis 4.8 Javascript library. and I'm stuck on one point. I'm creating map with US states' layers and want to show highlight when hover or click on any state on map. But unfortunately, I'm not able to found any way how we can achieve this.

Below is the code which I write.

<!DOCTYPE html>
<html>
<head>
  <title>Hosted Feature layer</title>
    <link rel="stylesheet" href="https://js.arcgis.com/4.8/esri/css/main.css">
</head>
<body>

  <!-- Main content -->
  <section class="content pp-dashboard">
      <!-- Small boxes (Stat box) -->
      <div class="row">
          <div class="col-lg-12">
              <div id="viewDiv" style="height: 800px;"></div>
              <div id="searching">
                  <input type="text" name="name" id="searchInput">
                  <input type="submit" name="Search" id="searchBtn">
              </div>
          </div>
      </div>
      <!-- /.row -->
  </section>
  <script src="https://js.arcgis.com/4.8/"></script>
  <script>
    require([
          "esri/Map",
          "esri/views/MapView",
          "esri/layers/FeatureLayer",
          "esri/widgets/Legend",
          "esri/layers/GraphicsLayer",
          "esri/Graphic",
          "dojo/on",
          "dojo/dom",
          "dojo/domReady!"
        ], function(
          Map, MapView, FeatureLayer, Legend, GraphicsLayer, Graphic, on, dom
        ) {

          let tempGraphicsLayer = new GraphicsLayer();

        var filteredGeometries;
        var searchInput = dom.byId("searchInput");
        var povLayer = new FeatureLayer({
            url: "https://services.arcgis.com/P3ePLMYs2RVChkJx/arcgis/rest/services/USA_States_Generalized/FeatureServer/0",
            outFields: ["*"]
        });

        var map = new Map({
            basemap: "dark-gray",
            layers: [povLayer]
        });

        var view = new MapView({
            container: "viewDiv",
            map: map,
            center: [-99.244309, 40.004476],
            zoom: 5
        });


        view.on('click', (event) => {
          view.hitTest(event)
            .then((res) => {
              console.log("length",res.results);
              if (res.results.length > 1) {
                return
              }

              let clickedResultData = res['results'][0];
              let stateCode = clickedResultData["graphic"]['attributes']['state_abbr'];
              let stateName = clickedResultData["graphic"]['attributes']['state_name'];
              console.log("clickedResultData", clickedResultData);

            });
        });


        view.ui.add("searching", "bottom-right");

        /******************************************************************
         *
         * Add layers to layerInfos on the legend
         *
         ******************************************************************/

        var legend = new Legend({
            view: view,
            layerInfos: [
            {
              layer: povLayer,
              title: "Poverty in the southeast U.S."
            }]
          });

          view.ui.add(legend, "top-right");


    });

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

In my code, I'm using FeatureLayer to read US states from FeatureLayer url. and all the states are drawing something like this.

enter image description here

Now my requirement is that, when user click on any state on map then that state should highlight and when user click on another state then previous selected state should de-select and newly selected state should show highlight.


Solution

  • I found a way to show highlight state when hover/click on any state on map. Below is the full code.

    <!DOCTYPE html>
    <html>
    <head>
      <title>Hosted Feature layer</title>
        <link rel="stylesheet" href="https://js.arcgis.com/4.8/esri/css/main.css">
    </head>
    <body>
    
      <!-- Main content -->
      <section class="content pp-dashboard">
          <!-- Small boxes (Stat box) -->
          <div class="row">
              <div class="col-lg-12">
                  <div id="viewDiv" style="height: 800px;"></div>
                  <div id="searching">
                      <input type="text" name="name" id="searchInput">
                      <input type="submit" name="Search" id="searchBtn">
                  </div>
              </div>
          </div>
          <!-- /.row -->
      </section>
      <script src="https://js.arcgis.com/4.8/"></script>
      <script>
        require([
              "esri/Map",
              "esri/views/MapView",
              "esri/layers/FeatureLayer",
              "esri/widgets/Legend",
              "esri/layers/GraphicsLayer",
              "esri/Graphic",
              "dojo/on",
              "dojo/dom",
              "dojo/domReady!"
            ], function(
              Map, MapView, FeatureLayer, Legend, GraphicsLayer, Graphic, on, dom
            ) {
                let highlight;
                let tempGraphicsLayer = new GraphicsLayer();
    
                var filteredGeometries;
                var searchInput = dom.byId("searchInput");
                var povLayer = new FeatureLayer({
                    url: "https://services.arcgis.com/P3ePLMYs2RVChkJx/ArcGIS/rest/services/USA_States_Generalized/FeatureServer/0",
                    outFields: ["*"]
                });
    
                var map = new Map({
                    basemap: "dark-gray",
                    layers: [povLayer]
                });
    
                var view = new MapView({
                    container: "viewDiv",
                    map: map,
                    center: [-99.244309, 40.004476],
                    zoom: 5
                });
    
                view.on("pointer-move", eventHandler);
                view.on("pointer-down", eventHandler);
                view.on("click", eventHandler);
    
                function eventHandler(event) {
                    // the hitTest() checks to see if any graphics in the view
                    // intersect the given screen x, y coordinates
                    view.hitTest(event)
                      .then((res) => {
                            console.log("length",res.results);
                            if (res.results.length < 1) {
                                return
                            }
                            view.graphics.removeAll();
    
                            // create a new selected graphic
                            let selectedGraphic = new Graphic({
                                geometry: res.results[0].graphic.geometry,
                                attributes: res.results[0].graphic.attributes,
                                symbol: {
                                    type: "simple-fill",
                                    // style: "polygon",
                                    color: "orange",
                                    // size: "12px", // pixels
                                    outline: { // autocasts as new SimpleLineSymbol()
                                        color: [255, 255, 0],
                                        width: 2 // points
                                    }
                                }
                            });
    
                            // add the selected graphic to the view
                            // this graphic corresponds to the row that was clicked
                            view.graphics.add(selectedGraphic);
                      });
                }
    
                var legend = new Legend({
                    view: view,
                    layerInfos: [{
                        layer: povLayer,
                        title: "Poverty in the southeast U.S."
                    }]
                });
    
                view.ui.add(legend, "top-right");
    
    
        });
    
        </script>
    </body>
    </html>
    

    I think this will help anyone.