Hi all,
I am new to Qt and QML though I have experience in .Net. I am using the samples provided in the appstudio to create an offline mobile app that will permit searching and eventually routing.
I am stuck at trying to be able to search/find a POI using a locator which I have authored and packaged to an MMPK. I can load and view the contents just fine but geocoding based on the example is just not working.
It would appear that I cannot bind my search (text) field to the locator suggestions searchText
Does anyone have an example of offline geocoding using an MMPK locator?
I found that the sample works with mods to the url property but I do have to unpack the package, and set the url to the .loc file.
Solved! Go to Solution.
Hey Tanner,
So, I found that doesn't work, but this does:
onTextChanged: {
console.log("Text changed: " + findText);
//currentLocatorTask.suggestions.suggestParameters.maxResults = 50; //errors out (TypeError: Value is null and could not be converted to an object
var suggestParams = ArcGISRuntimeEnvironment.createObject("SuggestParameters");
suggestParams.maxResults = 15;
currentLocatorTask.suggestions.suggestParameters = suggestParams;
currentLocatorTask.suggestions.searchText = findText;
}
Thanks again for your responses!
Hi Smithse, hopefully I can be of some help. It looks like your workflow of connecting to the LocatorTask's url property to the .loc file is correct, but you can also get a LocatorTask property from a loaded MobileMapPackage. If you'd like to avoid having to unpack or load an MMPK, you can also create a .loc file directly from ArcGIS Pro with the Create a locator geoprocessing tool.
If you'd like additional code to reference, you can take a look an another Offline Geocode sample in our Qt samples repo. That makes use of a .loc file for San Diego that you can test your code with.
Let me know if that helps, and I'm happy to provide any other assistance if necessary!
Hi Tanner,
Thanks for the response. That sample was very helpful in getting my first bit of code working, and is what I derive my working code from currently. For the life of me however, I cannot seem to be able to bind and get suggestions from the LocatorTask property of the loaded MMPK.
My hacked together code currently consists of loading the map from the MMPK, and using the .loc from the same package, after is is unpacked. I guess I am essentially duplicating the data and just looking for a way to avoid this.
Cheers,
Sean
Hm, if I understand correctly, you're able to get the locator task from your loaded MMPK but unable to retrieve any LocatorTask.suggestions when you create it that way. But you're able to get the suggestions when you create a LocatorTask component with a .loc file. I hope I have that correct.
Without seeing your code, I'm wondering if your LocatorTask is being instantiated correctly from the MMPK. It can be a little odd, so you might want to check out our MobileMap_SearchAndRoute sample, where we get a LocatorTask from an MMPK rather than creating a component with a URL or path to a .loc file. Is there any possibility you can share some of your code? Alternatively, is there a way you can check if there are load errors or geocode errors? You can check with the following code block:
Connections {
target: locatorTask // the name of your locator task property
function onLoadErrorChanged() {
// Catch any errors when loading the task
console.log(locatorTask.loadError.message, locatorTask.loadError.additionalMessage);
}
function onGeocodeStatusChanged() {
// Catch any errors in the geocode process
if (locatorTask.geocodeStatus === Enums.TaskStatusErrored) {
console.log(locatorTask.error.message, locatorTask.error.additionalMessage);
}
}
function onErrorChanged() {
// Catch any other general errors
console.log(locatorTask.error.message, locatorTask.error.additionalMessage);
}
}
Thank you, I hope that helps, and sorry for the trouble!
Hi again, Tanner,
Thanks for the response and please, no apologies needed! 😀
Below is some of the code: it's ugly as it's been chopped down to try and resolve this suggestions issue. When I get the LocatorTask from the MMPK, I don't seem to be able to set the suggestions.searchText property. Maybe this is what I am doing wrong and is the issue (here's hoping!)
The code you provided closely matches mine, with the exception of the onErrorChanged() function, so I will play around with that and see if anything shows up. In the meantime, here's bits of what I have... and this all works fine. It would just be nice to not have to use two LocatorTask(s).
//MapView - when map changes, instantiate a locator
//This code has been made as short as possible as I am not looping though files and folders. We simply load the map and use (try to) the locator from the package
onMapChanged: {
mapView.resetMap();
// change the locatorTask: messed around here making sure it loaded
mmpk.locatorTask.objectType === "LocatorTask" ? mapLocatorTask = mmpk.locatorTask: mapLocatorTask = null
// determine if map supports routing
if (mapView.map.transportationNetworks.length > 0) {
currentRouteTask = ArcGISRuntimeEnvironment.createObject("RouteTask", {transportationNetworkDataset: mapView.map.transportationNetworks[0]});
currentRouteTask.load();
}
else {
currentRouteTask = null;
}
}
//------------------BEGIN MobileMapPackage -------------------
property string packageName: "QuikMap"
property string sharedDataPath: AppFramework.resolvedPathUrl(
AppFramework.userHomeFolder.filePath("ArcGIS/AppStudio/Data/")) + "/";
property string packageFileNameWithPath: sharedDataPath + packageName + ".mmpk"
MobileMapPackage {
id: mmpk
path: packageFileNameWithPath
onLoadStatusChanged: {
if (loadStatus !== Enums.LoadStatusLoaded)
return;
mapView.map = mmpk.maps[0];
//Todo: some checks here about the mmpk that is being loaded
//Note: have also tried to instantiate the mapLocatorTask from here...
}
Component.onCompleted: {
mmpk.load();
}
}
//------------------END MobileMapPackage -------------------
//This is the locator task that works when pointing to a .loc
LocatorTask {
id: locatorTask
url: locatorUrl //path to the .loc from the unpacked mmpk
suggestions.suggestParameters: SuggestParameters{
maxResults: 50
preferredSearchLocation: currentViewPointCentre
}
suggestions.searchText: searchTextField.text
onGeocodeStatusChanged: {
if (geocodeStatus === Enums.TaskStatusCompleted) {
if(geocodeResults.length>0){
//code ommitted for clarity
}
}
}
}
Cheers again,
Sean
So... I think I have one of the errors of my ways 🙂
With the LocatorTask declared (as in the bottom of the snippet above) and the suggestions.searchText bound to the TextField, a change to that textfield caused the suggestions to be generated.
When the LocatorTask in the mmpk is used, the suggestions do not get returned.
What I have done now, is explicitly call or should I rather say, set, the property when the value of the text field changes, like this:
mmpk.locatorTask.suggestions.searchText = searchText;
This does return suggestions, but only 5 and I cannot see how to change the maxResults parameter when the locator is pointing to the package LocatorTask.
Any suggestions? <- no pun intended 🤣
Once I get this working, I will post a complete snippet as it may help someone else in the future.
Are you able to update the SuggestParameters.maxResult property? That would look like this:
`mmpk.locatorTask.suggestions.suggestParameters.maxResults = 10; // or some number`.
Hey Tanner,
So, I found that doesn't work, but this does:
onTextChanged: {
console.log("Text changed: " + findText);
//currentLocatorTask.suggestions.suggestParameters.maxResults = 50; //errors out (TypeError: Value is null and could not be converted to an object
var suggestParams = ArcGISRuntimeEnvironment.createObject("SuggestParameters");
suggestParams.maxResults = 15;
currentLocatorTask.suggestions.suggestParameters = suggestParams;
currentLocatorTask.suggestions.searchText = findText;
}
Thanks again for your responses!