Google maps in AB1


Peter Bradstreet
Hi David,

I hope that you are well. I am struggling with Google maps a bit and I was wondering if you would mind taking a quick look at my code. I am working originally from the Google Maps 3 sample and have it working with showing a single marker which then shows an infowindow on mouseover.

I am now trying to run a query in Firebase to return a number of records that I want to show as multiple markers on the map. Initially, I am just tryng to show markers for a series of manually stored locations and once I have it working, I will switch it to using dynamic data.

I am having an issue with the correct syntax for converting some code that I found online to be accepted by the AB code editor. Here is the code:

The specific section that is obviously wrong and won't compile is this portion:

Any assistance would be greatly appreciated! ...Pete


decsoft

Hello Peter,

If we talk specifically about the code that you shown, certainly there is a syntax error: a missing end bracket in the "for":



Peter Bradstreet

Thanks! I should have seen that.

Pete

decsoft

Glad to know that you finally got it Peter! ;-)



Peter Bradstreet
Hi David,

Still pounding away on Google maps and I have it working so that if you click on a map marker it pops up an infowindow that displays html content. In that content I want to have a button that takes the user to a different AB view. I was thinking that the best way to do this was to place a hidden button (HiddenButton1) on the map view and then have the button in the infowindow trigger the hidden button to go to the details view.

The js code snippet that sets the content of the infowindow is as follows:

When I click on the button in the marker infowindow I get the following console error: "SyntaxError: '' string literal contains an unescaped line break".

I was wondering whether this is the right approach and if so, what the correct syntax would be for the infowindow button or whether I am totally off base and there is a better way to handle this?

Thanks!
Pete

decsoft

Hello Peter,

Checking your code in this online tool, apparently there is no problem. So, I suspect that maybe a code like that (particularly the "onclick" event) can cause some problems... or... anyway... maybe it's required more information about, a possible sample app to reproduce the problem, for example.

However, I think there is a better approach: identify the button, place some information inside in a "data" attribute (optionally, I do it below because I like it), and then, use a jQuery event delegate in order to be ready for the button's click. Doing that, we no need to place any event in the button itself, which can cause undesired problems like you experience.

The below code is all what we need, and, can be placed in the app view Show event, in order to initialize the map, place a sample marker, and prepare the appropriate marker's info window, with a button inside, which go to another app view when it's pressed.

Below you have the complete sample app for AB1: save the XML into a "MyApp.ab" file, and open it with AB:

Remember to set your Google Maps API key (using the app Files Manager).



Peter Bradstreet
Hi David,

As always you went above and beyond, thanks for the help!! I have your sample working so I will dissect it and apply your approach to my app.

Thanks again!
Pete

decsoft

No problem, Peter! Thanks for your kindly words! :-)



Peter Bradstreet
Hi David,

I am making good progress on the Google mapping stuff and have maps that are showing single markers with popup info windows that contain a more details link that takes the user to another view with the relevant details. (Thanks for your help in getting that working)

I am now working on a view that returns a firebase query of vessels and displays each of them as a marker in the view google map.

I have multiple markers showing right now in the map but the markers are defined in a manually coded array

My query results however are returned as objects rather than an array and I am at a loss how to create a similar array as above but with the returned object data.

Below you can see the code in the view code that returns the objects and you can see that I am currently writing the results to the console which is shown in the bottom code block.

Here is the console log text:

Any advice on converting the returned objects to an array would be hugely appreciated!

Cheers, Pete

Peter Bradstreet

Not sure if it is useful, but here is the full view show code:


decsoft

Hello Peter,

I am not completely sure about the specific source objects, but, figure out that you have an Array of Objects variable (apparently this is the source), and, what you wanted is an Array of Arrays variable (this is what the "locations" variable is), take a look at the below code, which I hope that can help you giving you the idea of what you must to do:

App Builder's code:

JavaScript code:

Both pieces of codes produces the same result.

Note for the readers: the above App Builder code refers to the previous generation of the DecSoft App Builder. The new generation of DecSoft App Builder don't provide "actions" like the previous generation do, but we can directly write JavaScript code instead.


Peter Bradstreet
Hi David,

Thanks for your help, I feel that I am close but am getting an undefined error.I went with your js example:

I tried to replace your sample array source with the objects returned from the firebase query:

The results of the console log: console.log(window.App.RootScope.SourceObjects); is returning what appears to be valid objects:

However, we I run the view and view the console I am getting an error: TypeError: window.App.RootScope.SourceObjects is undefined. The line that seems to be causing this error is:

for (var i = 0; i < window.App.RootScope.SourceObjects.length; i++)

This is confusing to me because it seems that SourceObjects must be defined since I can view it in the console log and my code is very similar to yours which works. Any ideas?

Cheers, Pete

decsoft

Hello Peter,

The idea of my code is to show you how to "convert" an Array of objects to your desired Array of arrays variable, but, I think the below can't do the job:

Certainly you are assigned some data to the "SourceObjects" variable, but, nothing happend then, you did not apply the code there, or, I can't see it.

I think it's better to use the JavaScript version of my sample, since you are already dealing with JavaScript code, so, the code can looks like the below one:

However, note that the above code can't work as expected, because you must change the below:

... in order to match your objects properties: for example, in my sample there is a property "Name" in the samples objects, but, maybe that property don't exists in your objects, or, may you want to use another properties. My code is just a sample which uses ficticious objects.

If I did not provide to you a real sample (using your source of data) is because I am not sure about the source that you get. So, please, try the above, and, if you wanted, post here the server's response, that is, the content of the "doc.data()" variable, but, be sure that you copy here the complete JSON (the idea is that you can get it from the developer console, but, not copying what you paste here: instead of it, you must copy here the entire JSON response, even if it's unformatted, that is not a problem) so I can take a look it.

I mean post here the contents of the red rectangle, and not the contents of the blue rectangle:



Peter Bradstreet
Hi David,

I really appreciate your help as I am struggling with this. I have adapted an earlier sample that you sent me to try and fast track this. In View 1 I have a google map with a marker and infowindow. On view 2 I have a firestore query that returns two objects.

What I am trying to do is to leave the existing marker on the map on View 1 but also show two more markers based off of the query return along with infowindows for those markers with vessel name in infowindow. If you could let me know what I am doing wrong, it would be fantastic as I am spinning my wheels on this.

Sample: Download

Cheers, Pete

decsoft

Hello Peter,

If I am not wrong, it's not possible to remain the markers in the map, because, the map itself is gone once we move to another app view. So the app must be "recreated" when we back to the map view, to say like that, and, that's the moment again to prepare the right markers that we can show in the map. But this is not a problem, I think.

That is, certainly you can use a variable to feed the map of marks, to say like that: so that variable can be modified in another app view, so, when we go back to the map one, we simply set the markers again, including the possible new "marks information" which the referred variable includes. So in few words, the map nor markers are not "globals" and they are not "maintained", but, the app variables are, so we "feed the map" with that variables, wich can be changed in any of the app views.

Taking the above in consideration, let me how I can help you, Peter.



Peter Bradstreet
Hi David, Yes, I want everything to happen in View 1, I included View 2 just so that you could see that the query results are being returned as objects and I am showinig them in the report. That being said, View 2 is not necessary as same get query is in View 1. I am hoping that you could give me a hand getting View 1 to pull the query results in, convert them to an array and then show the array as markers on the map? Cheers, Pete

decsoft

Hello Peter,

The problem is that I can't get the response that you get from the server: I get some "permissions" error here and not the desired array of objects. So just place here the JSON response (remove any possible private information if needed) and I will try to help you.



Peter Bradstreet
Hi, I have relaxed the security rules so you should be able to get a return now. Pete

decsoft

Hello Peter,

There are various things to consider here. One thing require to take a look at the below code:

We have what we expected inside "querySnapshot", but, this is not an Array of Objects variable. In fact, to get access to the records sent to us by the server, we must use what you already do: the "forEach" over the "querySnapshot" variable, and then, once we get the "doc", retrieve the record using the "doc.data()" method.

So in fact you no need to convert any Array of objects variable to any Array of arrays variable: you can just prepare your Array (with markers information) in a way like the below one:

But here is the other thing to be considered: you can't just initiate the map and prepare the markers just by write the right code below the above code, because that code is executed in an asynchronous, so, if you write something like the below:

... the "alert" is executed before our "markersInfo" variable has been completely feed. So what to do? Just wait for the variable to be feeded:

The "initMap()" function is executed when our "markersInfo" variable is already feeded, so, we can then create the map, and then iterate the Array variable to place the right marks inside the map. All the code is below: you can place in the Show event of the "View1" of the sample app that you linked before:

May we can enhance the above code, for example, to move the "initMap" and other functions into the "app functions manager", or maybe some changes are required, but, I hope that that code can help you to give an idea at least. Post here if you have further question, Peter.



Peter Bradstreet

Many thanks David!

I would like to push some of the marker data into the infowindow. In your sample, you are putting the markersInfo[i] into a var called info and you are using info.VesselName to set the title of the marker. However, since the info window is defined in it's own function, the info var is not defined within that function and is not available. How would I access the data related to that vessel inside the info window?

I would need to defined the contentStr with something like:

Cheers,

Pete


decsoft

Hello Peter,

We can add to the marker the information if we need it. The "showInfoWindow" receive the marker as his argument, so, we can access to the marker's information as well. Just take a look at the below code, which is a modification of my latest one:



Peter Bradstreet
David,

I can't thank you enough for all of your help, I am finally starting to get a handle on this! I think that I have a handle on all of my mapping requirements now and will spend some time polishing it, then on to instant messaging.

Cheers, Pete

decsoft

No problem, Peter! :-)


Everybody can read the DecSoft support forum for learning purposes, however only DecSoft customers can post new threads. Purchase one or more licenses of some DecSoft products in order to give this and other benefits.

This website uses some useful cookies to store your preferences.

I agree. Hide this note. Give me more information.