ichivite-esristaff

Pulling data from geopoint questions

Blog Post created by ichivite-esristaff Employee on Nov 2, 2016

In a previous post, we explored how expressions in the calculation column of your XLSForm could be used to programmatically set values on a geopoint question. In this occasion, we will do the opposite. That is, we will describe how you can extract data out of a geopoint. Here are some good reasons why you may want to do this:

 

  • Storing geopoint properties as attributes: Often times, keeping the X/Y coordinates of a point encoded in a geometry field is not ideal.  By pulling data out of a geopoint question you can store the X/Y coordinates in specific fields. You can also extract and store other values from your geopoint properties such as the elevation, speed or horizontal accuracy if present. Having all these values as attributes can help during QA/QC as well as data exchange processes.
  • Enforcing constraints and relevant statements: Say you want to prevent users from capturing coordinates outside of a particular extent, or ensuring that the elevation values are within a particular range. Expressions in the relevant column can be used to present users with more or fewer questions in the event that specific properties of a geopoint are met.

 

What a geopoint is made of?

 

We all know that geopoint questions store location information, but what is really inside a geopoint value? At a minimum, unless a geopoint question is empty, you will always find the latitude and longitude of a location. Survey123 never works with projected coordinates: geopoint values are always in geographic coordinates using WGS84.  Now, you could potentially find much more than just a latitude/longitude pair within a geopoint value:

 

 

Property NameDescriptionUnits
xLongitude, positive in eastern hemisphere, negative in western hemisphere

Decimal degrees

y

Latitude, positive in northern hemisphere, negative in southern hemisphere

Decimal degrees

z

Altitude, meters above sea level

Meters

horizontalAccuracy

Horizontal accuracy of the x and y coordinates

Meters
verticalAccuracy

Vertical accuracy of the z coordinate

Meters
speedGround speed

Meters per second

verticalSpeedVertical speed

Meters per second

direction

Direction of travel measured clockwise from north

Decimal degrees

magneticVariation

Angle between magnetic and true north

Decimal degrees

 

If a geopoint question contains all the properties above or a subset, depends on the following:

 

  •  If the location is set by the end user by manually tapping on the map, then only the x an y properties will be populated. It is possible to also let the user type the elevation, which ultimately would popupate the z property. 
  • If the location is set by the device, the number of properties with data will depend on the device. The accuracy of the values found in each property is as well completely dependent on the device providing the location information to Survey123.

 

If relying on consumer devices to retrieve the location properties above, you should take values with a grain of salt. Your average iPad or Android smartphone could often give you a reasonable x,y and horizontal accuracy but everything else could or could not be trustworthy. In fact, many consumer devices do not even populate most of the properties above. I do not want to say consumer devices will give you useless geopoint  properties, but you should proceed with caution understanding through trial and error what devices and in what conditions will give you accurate information. 

 

Proper use of external GNSS receivers to augment the readings from the location services in your device is often the best approach to get the above properties with reliable values.  There is a wide collection of options for such GNSS receivers, many of them providing very reliable information even at  the lower-end of the price spectrum.

 

If using external GNSS receivers, metadata such as 'Fix Type', 'Receiver', 'PDOP','HDOP','VDOP', 'Number of Satellites' or 'Fix time' will not be persisted in the geopoint. Storing this metadata from the external receiver is a feature that may be considered for upcoming releases.

 

 

            Warning for iOS users using external GNSS receivers: While external GNSS receivers, when used properly, will typically provide more consistent and accurate location information than your iOS device, you should be aware that the iOS operating system will never report horizontal accuracy better than 5 meters, even if in fact your GNSS receiver will be giving you more accurate data than 5 meters.  This behavior is unique to iOS, not affecting Android or Windows devices.  In general, and as of the current release of Survey123, the external GNSS receiver signal is not read directly by Survey123. Instead, the GNSS receiver data is processed through your devices Location Services API.

 

Reading geopoint properties using the pulldata function

 

All the geopoint properties described above can be extracted using the pulldata function.

 

pulldata("@geopoint", ${location}, "horizontalAccuracy")

 

The "@geopoint" parameter  to the pulldata function indicates that values will be extracted from a geopoint value.

The second parameter indicates the question in your XLSForm that holds the actual geopoint value. You will want to make sure that the question you reference is actually of type geopoint.

The third and last parameter defines which of the properties in the geopoint value you want to extract. You will want to make sure the property name is included in the table above and make sure that you specify it with the proper capitalization: HorizontalAccuracy is not the same as horizontalAccuracy.

 

 

Learning by Example:

 

Here is a simple XLSForm that will extract the X,Y and Horizontal Accuracy of your geopoint and store these values as attributes. Using this technique, you have complete freedom as to which fields in your feature service will be  used to store the geopoint properties.  You use the Name column in the XLSForm to define which field will keep the data.

 

TypeNameLabelCalculation
geopointlocationLocation
decimalLatitudeLatitudepulldata("@geopoint", ${location},"y")
decimalLongitudeLongitudepulldata("@geopoint", ${location},"x")
decimalHorAccMetersAccuracypulldata("@geopoint", ${location},"horizontalAccuracy")

 

Realistically, I would never store geopoint properties as illustrated in the example above. Mostly because I would not want end-users to get distracted with questions in the survey that get automatically populated with these properties. I would not want end-users to modify these calculated values either. 

 

A more  refined approach would be to set  the Type of question as hidden. In this way, the Latitude, Longitude and Accuracy questions would not be shown in the form, but their information would still be sent to the feature service on submit. To ensure  the actual values are stored as numbers in the feature service, I would also set the esriFieldType column to esriFieldTypeDouble as shown here:

 

TypeNameLabelCalculationbind::esri:fieldType
geopointlocationLocation
hiddenLatitudeLatitudepulldata("@geopoint", ${location},"y")esriFieldTypeDouble
hiddenLongitudeLongitudepulldata("@geopoint", ${location},"x")esriFieldTypeDouble
hiddenHorAccMetersAccuracypulldata("@geopoint", ${location},"horizontalAccuracy")esriFieldTypeDouble

 

When working with horizontal accuracy, you should also learn about the meaning of the accuracyThreshold column.

 

You can use very similar expressions in your constraints and relevant statements. In the next example, we will pop a message in case that the geopoint value was captured while moving faster than 0.2 meters per second.

 

TypeNameLabelRelevant
geopointlocationLocation
calculateHAHA pulldata("@geopoint", ${location},"speed")
noteDo not move while fixing location!0.2<number(${HA})

 

Like every time you use pulldata() it is best practice to use this function alone. This is why I broke down my last example into two separate questions: One calculate question to invoke pulldata() and a separate question where I compare the output of the pulldata function with a number.

Outcomes