Select to view content in your preferred language

Can't zoom to feature from Datagrid

4065
26
Jump to solution
06-09-2014 05:37 AM
RyanSellman
Deactivated User
I have a find task in my application that returns features that are points, lines and polygons.  I can get the search to populate the datagrid but I am having problems with my onRowClickHandler function and zooming to those features from the datagrid.  I've been searching through the forums and see that zooming to a point from the datagrid has been an issue for others, but I can't find a solution that works for me.  Here is some code that shows the findtask and what I have for the onRowClickHandler function.

I get the error: "Uncaught TypeError: Cannot read property 'getExtent' of undefined" when the onRowClickHandler function is fired.


findDistrictTask = new FindTask("http://summitgis.summitoh.net:6080/arcgis/rest/services/DOES/MapServer/");          map.on("load", function () {             findDistrictParams = new FindParameters();             findDistrictParams.returnGeometry = true;             findDistrictParams.layerIds = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];             findDistrictParams.searchFields = ["NAME, UNAME, PUMPID, PIPEID, PlantID, Name"];             findDistrictParams.outSpatialReference = map.spatialReference;         });          function doDoesDistrictFind() {             findDistrictParams.searchText = dom.byId("doesDistrictText").value;             findDistrictTask.execute(findDistrictParams, showResults);         }           function showResults(results) {             var markerSymbol = new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_SQUARE, 10, new SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_SOLID, new dojo.Color([255, 0, 0]), 1), new dojo.Color([0, 255, 0, 0.25]));             var lineSymbol = new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_DASH, new dojo.Color([255, 0, 0]), 1);             var polygonSymbol = new esri.symbol.SimpleFillSymbol(esri.symbol.SimpleFillSymbol.STYLE_NONE, new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_DASHDOT, new dojo.Color([255, 0, 0]), 2), new dojo.Color([255, 255, 0, 0.25]));             map.graphics.clear();             var dataForGrid = [];             arrayUtils.map(results, function (result) {                 var graphic = result.feature;                 dataForGrid.push([result.layerName, result.foundFieldName, result.value]);                 switch (graphic.geometry.type) {                 case "point":                     graphic.setSymbol(markerSymbol);                     break;                 case "polyline":                     graphic.setSymbol(lineSymbol);                     break;                 case "polygon":                     graphic.setSymbol(polygonSymbol);                     break;                 }                 map.graphics.add(graphic);             });             var data = {                 items: dataForGrid             };             var store = new ItemFileReadStore({                 data: data             });              var grid = registry.byId("grid");              grid.setStore(store);             grid.on("rowclick", onRowClickHandler);              map.centerAndZoom(center, zoom);         }          function onRowClickHandler(evt) {             var clickedFeature = evt.grid.getItem(evt.rowIndex).OBJECTID;             var selectedFeature = arrayUtils.filter(map.graphics.graphics, function (graphic) {        return ((graphic.attributes) && graphic.attributes.OBJECTID === clickedFeature);       });        var featureExtent = selectedFeature.geometry.getExtent();    var screenpoint = map.toScreen(selectedFeature.geometry.getExtent().getCenter());    var mappoint = map.toMap(screenpoint);        map.centerAt(mappoint);                 if (selectedFeature.geometry.declaredClass == 'esri.geometry.Point') {                 map.centerAt(selectedFeature.geometry);             } else {                 var featureExtent = selectedFeature.geometry.getExtent();                 var screenpoint = map.toScreen(selectedFeature.geometry.getExtent().getCenter());                 var mappoint = map.toMap(screenpoint);                 map.centerAt(mappoint);             }       } 


Does anyone have any idea what I am doing wrong or a way to zoom to all feature types from a datagrid?  Thanks in advance!!!
0 Kudos
26 Replies
RyanSellman
Deactivated User
I have tried that with no luck, but with a different error:

This:
function onRowClickHandler(evt) {
     var grid = registry.byId("grid");
              var clickedObjectf = evt.grid.getItem(evt.rowIndex).OBJECTID;
              var selectedObjectf;
              var distance = 50;
              dojo.forEach(map.graphics.graphics, function (graphicf) {
                  if ((graphicf.attributes) && graphicf.attributes.OBJECTID === clickedObjectf) {
                      selectedObjectf = graphicf;
                      return;
                  }
              });
              if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Point') {
                  var PointExtent = new esri.geometry.Extent({
                      "xmin": selectedObjectf.geometry.x - distance,
                      "ymin": selectedObjectf.geometry.y - distance,
                      "xmax": selectedObjectf.geometry.x + distance,
                      "ymax": selectedObjectf.geometry.y + distance,
                      "spatialReference": {
                          "wkid": 102100
                      }
                  });
                  map.setExtent(PointExtent);
              } else if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Polygon') {
                  var selectedParcel = selectedObjectf.geometry.getExtent();
                  map.setExtent(selectedParcel);
              }
          }


returns this error:

"Uncaught TypeError: Cannot read property 'geometry' of undefined"

at this line of code:
if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Point') {
0 Kudos
KenBuja
MVP Esteemed Contributor
Are you sure you're assigning a value to selectedObjectf  in this section of your code?

dojo.forEach(map.graphics.graphics, function (graphicf) {
    if ((graphicf.attributes) && graphicf.attributes.OBJECTID === clickedObjectf) {
        selectedObjectf = graphicf;
        return;
    }
});


I would suggest you start learning how to debug your code using some of the build-in developer tools in the different browsers. There's a video of the session "Tips and Tricks for Debugging Apps Built with ArcGIS API for JavaScript" here that you can watch.
0 Kudos
RyanSellman
Deactivated User
Ken,

I appreciate your help with this as well as the resource you have given me.  I will definitely watch it and continue to plug away at this.

Best,
Ryan
0 Kudos
LuciHawkins
Frequent Contributor
Hey Ryan,

In my app I use the variable "graphicf".  In your routine, you use the variable "graphic".  Ken was onto something.  Change graphicf to graphic (in all places in the onRowClickHandler)  and see if that works.

Thanks,

Luci
0 Kudos
RyanSellman
Deactivated User
Hi Luci,

Thanks for the note!  I made the changes throughout the function but I still can't get it to work correctly.  I have the following code in my app and it says it can't read the property 'geometry' of undefined.

function onRowClickHandler(evt) {
var clickedObjectf = grid.getItem(evt.rowIndex).OBJECTID;
var selectedObjectf;
var distance = 50;
dojo.forEach(map.graphics.graphics, function(graphicf) {
if ((graphicf.attributes) && graphicf.attributes.OBJECTID === clickedObjectf) {
selectedObjectf = graphicf;
return;
}
});
if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Point'){
var PointExtent = new esri.geometry.Extent({
"xmin" : selectedObjectf.geometry.x - distance,
"ymin" : selectedObjectf.geometry.y - distance,
"xmax" : selectedObjectf.geometry.x + distance,
"ymax" : selectedObjectf.geometry.y + distance,
"spatialReference" : {
"wkid" : 102100
}
});
map.setExtent(PointExtent);
}
else if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Polygon'){
var selectedParcel = selectedObjectf.geometry.getExtent();
map.setExtent(selectedParcel);
}
}


From one of the samples on the API site, I tweaked it a little.  Still not working but I get a new error that says it can't read the property declaredClass of undefined.

function onRowClickHandler(evt) {
        var clickedObjectf = evt.grid.getItem(evt.rowIndex).OBJECTID;
 var selectedObjectf = arrayUtils.filter(map.graphics.graphics, function (graphicf){
  return ((graphicf.attributes) && graphicf.attributes.OBJECTID === clickedObjectf);
 });
 var distance = 50;
 if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Point') {
  var PointExtent = new esri.geometry.Extent({
   "xmin": selectedObjectf.geometry.x - distance,
   "ymin": selectedObjectf.geometry.y - distance,
   "xmax": selectedObjectf.geometry.x + distance,
   "ymax": selectedObjectf.geometry.y + distance,
   "spatialReference": {
    "wkid": 102100
   }
  });
  map.setExtent(PointExtent);
 } else if (selectedObjectf.geometry.declaredClass == 'esri.geometry.Polygon') {
  var selectedParcel = selectedObjectf.geometry.getExtent();
  map.setExtent(selectedParcel);
 }
}


I really don't know what I am doing wrong, but I will continue to plug away in hopes of a solution.

Thanks again for your suggestion and help!

Ryan
0 Kudos
RyanSellman
Deactivated User
Okay so I think I got it working...part of the problem was that my onRowClickHandler function couldn't handle point features, but as indicated above, the suggestions for this function still didn't get things working. The showResults function was the larger part of the problem. Initially, the info being pushed to the datagrid was the resulting layer name, found field name and found value. I wanted to employ this method since I am searching a service with multiple layers and returning all records to one datagrid - so a search could potentially return results from multiple layers if the criteria isn't specific enough. For some reason, the onRowClickHandler function couldn't get at the geometry of each feature returned. Here is the code that had been giving me issues:

function showResults(results) {
              if (results.length > 0) {
                  map.graphics.clear();
                  var markerSymbol = new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_SQUARE, 10, new SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_SOLID, new dojo.Color([255, 0, 0]), 1), new dojo.Color([0, 255, 0, 0.25]));
                  var lineSymbol = new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_DASH, new dojo.Color([255, 0, 0]), 1);
                  var polygonSymbol = new esri.symbol.SimpleFillSymbol(esri.symbol.SimpleFillSymbol.STYLE_NONE, new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_DASHDOT, new dojo.Color([255, 0, 0]), 2), new dojo.Color([255, 255, 0, 0.25]));

                  var dataForGrid = [];

                  arrayUtils.map(results, function (result) {
                      var graphic = result.feature;
                      dataForGrid.push([result.layerName, result.foundFieldName, result.value]);
                      switch (graphic.geometry.type) {
                      case "point":
                          graphic.setSymbol(markerSymbol);
                          break;
                      case "polyline":
                          graphic.setSymbol(lineSymbol);
                          break;
                      case "polygon":
                          graphic.setSymbol(polygonSymbol);
                          break;
                      }
                      map.graphics.add(graphic);
                      return result.feature.attributes;
                  });
                  var data = {
                      items: dataForGrid
                  };
                  var store = new ItemFileReadStore({
                      data: data
                  });

                  var grid = registry.byId("grid");

                  grid.setStore(store);
                  grid.on("rowclick", onRowClickHandler);

                  map.centerAndZoom(center, zoom);
              } else {
                  alert("No Utility Feature found!  Please enter a valid UNAME, PIPEID, Plant ID, PUMPID or Name.");
              }
          }


I adjusted it with the below code, and now the onRowClickHandler routine (provided to me by Luci) is working for all feature types.

function showResults(results) {
              if (results.length > 0) {
                  map.graphics.clear();
                  var markerSymbol = new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_SQUARE, 10, new SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_SOLID, new dojo.Color([255, 0, 0]), 1), new dojo.Color([0, 255, 0, 0.25]));
                  var lineSymbol = new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_DASH, new dojo.Color([255, 0, 0]), 1);
                  var polygonSymbol = new esri.symbol.SimpleFillSymbol(esri.symbol.SimpleFillSymbol.STYLE_NONE, new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_DASHDOT, new dojo.Color([255, 0, 0]), 2), new dojo.Color([255, 255, 0, 0.25]));

                var items = arrayUtils.map(results, function (result) {
                      var graphic = result.feature;
                      
                      switch (graphic.geometry.type) {
                      case "point":
                          graphic.setSymbol(markerSymbol);
                          break;
                      case "polyline":
                          graphic.setSymbol(lineSymbol);
                          break;
                      case "polygon":
                          graphic.setSymbol(polygonSymbol);
                          break;
                      }
                      map.graphics.add(graphic);
                      return result.feature.attributes;
                  });
                  var data = {
        identifier: "OBJECTID",
        label: "OBJECTID",
                      items: items
                  };
                  var store = new ItemFileReadStore({
                      data: data
                  });

                  var grid = registry.byId("grid");

                  grid.setStore(store);
                  grid.on("rowclick", onRowClickHandler);

                  map.centerAndZoom(center, zoom);
              } else {
                  alert("No Utility Feature found!  Please enter a valid UNAME, PIPEID, Plant ID, PUMPID or Name.");
              }
          }


Now, displaying attributes in a useful way in the datagrid will be the next challenge.

Thanks to all for helping me tackle this! It is much appreciated!

Ryan
0 Kudos
KenBuja
MVP Esteemed Contributor
Glad to hear you got it working.

You should click the check mark on the post that best answered your question (even if it's yours) to help those who may be searching on this topic later.
0 Kudos