 Hello, everybody, let's get started right now. So we are from HereMaps. We are a mapping and location services company. My name is Dylan Babs. I'm from Seattle, and I work in our developer relations group. And I'm here with two of my colleagues from Berlin. Over here we have Ignacio. He is the engineering manager for HarpGL. And then over here we have Nino, who's also an engineer for HarpGL. So a little bit about our company. I like to say we're a full-stack mapping company. So we do everything from collecting data. We have people all over the world, in local offices, driving around cars, kind of like what you see for street view cars, collecting data that is then compiled into our global map, which they can consume in many different ways, one of them being HarpGL, which we'll talk about later today. But you could also see our maps in places like navigation systems. So in North America and Europe, four out of five cars will have our maps in their navigation systems. And we're collecting a ton of data, nearly 28 terabytes daily. And in our cars that are collecting LiDAR, we're doing 700,000 points of data per second. And we're not just doing standard mapping. We also have some HD maps. So that could be maps for autonomous vehicles. And we've so far covered 600,000 kilometers for autonomous driving maps. So really all different sorts of mapping. But today we'll be talking about our new JavaScript product, which is called HarpGL. It's a 3D map web renderer. So this is going to be a library that you can put on your websites to display some really rich and custom 3D maps. So HarpGL has a couple key concepts, three that we wanted to build it on. The first is modern web tech. So we built it on WebGL for really fast and performant rendering. So it works with all modern browsers, sometimes the exception of Internet Explorer. The second principle we wanted to build on was open source. We really value community contributions. And it's really nice to have the community in mind when actually building this product. So during the workshop today, if you have any ideas or bug reports and such, we highly encourage you to create either a pull request or an issue on GitHub. That way we could really take your feedback into consideration for the next release. Then finally, the third principle we wanted to build HarpGL on was the flexibility and interoperability. So by this, we mean two things. One is that you could choose any data source that you want to put into HarpGL. Like I said before, we create our own data sources that you could use, but you're not limited to just using us. In fact, you could use some of our competitive data sources like Mapbox, Esri, TomTom. You're free to really mix and match HarpGL with whatever you want. Because it's open source, you're able to do that. And the second is not just data source, but also data type. We'll be providing vector tiles, which is a way to consume the map data, but really you could put on any type of data source or type that you want in there. Since it's built upon 3JS, you could put any type of 3D object in there as well. And so we made HarpGL for a couple reasons. The first is we have a product out there called Open Location Platform. This is something if you're like BMW, Daimler, and you're creating data pipelines of your cars around the world ingesting sensor data. Sensor data is basically the data that a car is collecting as it drives, maybe like the width of the road, how far it can see and such. This is a pipeline you could create to actually collect that data and view it online. And then so you'll actually need a lot of 3D use cases for this type of stuff. The second use case was high definition maps, what I mentioned earlier in the presentation. This is really important because you need visualization of different Z levels. Like say, for example, this bridge right here, you need to actually be able to distinguish what is below and what above. So 3D visualization can provide some very powerful debugging tools for this. And then finally, we have a new product coming out called Here Navigation on Demand, which is really a modern take on these navigation systems and cars using modern technology before a lot of it was native OSs that you put inside the vehicle. But now we're trying to experiment with maybe web use and such. So since HarpGL is a web product, you're able to do that. It's a really flexible technical architecture when it comes to in-vehicle infotainment and navigation systems. So today, we'll be doing a workshop. You'll be learning how to implement a bunch of different 3D web mapping situations and different features. So let's go ahead and enter this link into your browser. And that will take you to a GitHub workshop. So that's bit.ly.jsconf-harp. So this repo we have is called DevRelWorkshops. And we have a director in here called HarpGL, which links to directly to it. We also have a bunch of other of our developer API workshops in here as well. So if you enjoy this product and you want to learn more about some of our other company's offerings, feel free to browse around in here. So some prereqs for this workshop. You just need a laptop with a modern web browser, which I'm sure you all have. And then Node and MPM or Yarn installed. So in this workshop, we also have a few different resources listed here. We have the GitHub repo, which you could find all the open source code for our. We have a link to the documentation, which has all the information on the different classes, objects, and methods. And then we have the live examples, which is right over here. These are pretty helpful because you click around, view some different features you can implement, like the globe right here. But then you could also click View Source over here on the bottom right. And that'll take you directly to the code needed to run that example. So did anyone have trouble reaching the workshop link? Awesome. Great. So feel free to read ahead in the workshop. For the next 10 minutes or so, I'm going to be explaining some key concepts. But if I'm going too slow and you want to move faster, you're welcome to just read through the workshop. So in Harp, the high level object is called a map view. This is going to be the object that are going to be modifying and adding things to inside your map. So say, for example, you want to initialize a new map. You could just do harp equals new harp dot map view. You could pass to the canvas. That's going to be the HTML element on your page that you want to put the map in. Then you could also assign a theme. We have a couple different themes available, which you could use. For example, like normal day, light and dark. And you could also create your custom themes, which we'll be doing later on in the workshop. And then you could also choose a projection, which we'll talk about a little bit more later. So there's a very popular type of geographic data formats for the web. It's called GeoJSON. Have any of you guys heard of GeoJSON before? It's pretty easy to work with, mostly because it's just JSON, so nice for web development. And HarpGL uses many different types of GeoJSON. But there's two examples I'd like to point out here, just to get you guys familiar with the type. A point in a line. So if we take a look at the structure of GeoJSON, you have the type, which is mostly always going to be a feature. And then you have geometry. This is where you classify which type of geometry it will be. It could be a point. It could be a line. It could be a polygon or a multi-polygon. And then you could put the coordinates. And then there's also an object in here called properties. And this is where you could really assign any type of other properties you want to it. For example, you could say the name of it, really anything you want to put in there. And then a line is pretty much the same thing. The only difference is the type. Now it says line string in here. And then coordinates is now no longer just one array. It's an array with arrays of coordinates inside of it. So you'll be using GeoJSON later on in this workshop to actually put data onto the map. And GeoJSON is nice because it's pretty widely supported. So a lot of websites for open data will have GeoJSON you could download. And then another key concept we have is our styling syntax and also styling sheets. Because HARPGL is a vector render, that means we're calling the data from a server. And then we're rendering on the client. We need to actually bind style rules to it. So say, for example, you're looking at a map. A lot of time roads are yellow, the water's blue. That's because there's style rules defined for each type of property. So say, for example, here we're saying when the geometry type is a point, we want to use the technique of circles. So we want to draw circles. And then we want to make it this color. I have no idea what the 7ED color is. But you could really assign any CSS value in here you like. And then size could also be meters, points, or whatever. You could also clarify the metric in the unit for this. Then say, for example, for a polygon pretty much the same thing, we're just saying when geometry type equals polygon, we want to apply these styling rules. I don't have an example of it in here as well. But you could also style the same properties you saw back here in the point. So say we want to say, when we see the Dinnigat islands, we want to make it yellow. We would do when property equals name and Dinnigat islands, we would apply the certain style there. So with maps, many of you are probably familiar with the Mercator projection, also known as the Flat Earth. That's here on the left. It's a pretty standard map you see on web maps. It's pretty common, and I think people are used to it. So we'd like to see it. But technically, Mercator projections aren't too accurate, because the top and the bottom are slightly stretched out, because you're projecting a sphere into a rectangle. So to show you a cool example of this, there is a fun little website called The True Size that I like to show everyone and play around with. We can see we're taking the United States in the normal position right here. And if we drag it up to Greenland, we actually see that it gets moved around and grown much more. So for example, Greenland isn't actually that size. It's definitely much smaller if you drag it around here. So this is why we've also included a globe projection, because it's technically a more accurate view of the world. The world is a sphere, so it's nice to be able to represent it as a sphere in our maps. So you'll have the option of doing two different types of projections, the Mercator and Globe, with HarpGL. And you try them both out in the workshop. And then for data sources, I already mentioned vector tiles. This is when the data is being delivered from the server and you're running it on the client. It's really an optimized version of GeoJSON. But then you also have static GeoJSON. Say if you just want to make a normal fetch request or a network request to a static GeoJSON file you have in your local directory or another site, you could put that onto your map as well. But we also support raster tiles. So this is a great example of doing satellite imagery. A raster tile is basically just a smaller image. And then for those of you familiar with 3JS or other 3D objects, you could also put 3D objects onto the map. And then since it's open source, you are able to extend HarpGL however you want to add any type of data source you would like. And then in terms of consuming the API, we have two different ways. One is a pretty modern version with modules that you install via NPM in the ARM. But we also have a simple scripting API that you could add in via a script tag on your HTML. This is sometimes easier, and we'll be using the simple bundle in the workshop just because it'll get you started easier. If you're doing the modules, those work great because you're working with TypeScript, and you can really import which ones you want at the time. But sometimes it's a little frustrating just to get started with it because you have to fight with Webpack to get the right configuration and such. So today we'll be doing the scripting API. Awesome. So those are the key concepts for HarpGL. Hopefully that background information will help you out during the workshop. So the first thing we want to do is head on over to our developer portal. We have a link in the workshop. We scroll down past the key concepts. It will be developer.here.com slash events slash jscomp asian19. So in order to use HarpGL, you'll need to sign up on this site, and this will give you access to data. And the reason we have a special URL right here, it just helps with our tracking purposes, and it makes sure you get to the right key so you can use it with HarpGL. So we'll give everyone three to five minutes to go and sign up online. It's pretty simple. Click on it. Click Get Started for Free. No credit card or anything is required. You only just put in your name, your country, or email, and a password. So go ahead and click this right here. And once you sign up, feel free to take a look around our developer portal and see some of the other map services we have. We offer 250,000 transactions a month for free, which is pretty generous when comparing it against our competitors in the free tier. So 250,000 transactions is enough to keep a small startup floating monthly. And feel free to raise your hand if you have any questions, we'll be happy to come around and help. All right, awesome. How many of you have signed up? Cool, we'll give it maybe just one more minute. Great. So once you've signed up, we have one more small step to do to get credentials. If you go back to GitHub Repository right below the navigate to developer.here.com link, you'll see text that says, once you've created a developer account, navigate to the here XYZ token manager. So here XYZ is another one of our here products that's actually serving us the data. So this is where we'll get our token. So I'll go ahead and click on this link. And I'll see this little modal here. And I'll sign in with the developer account I just created about a minute ago. And then once I've logged into the token manager, I could either generate a new token, which I'm sure will be the case for you guys since you're a first time user. Or I can manage the tokens. But I'll generate a new token. I'm going to say token for harpgl workshop. I'm going to click generate. Oh, I need to actually select some writes. And then we have a new token up here generated. So I'd keep this window open because you'll be copying, pasting this token later on into your code. Or save it to a notepad or something like that. Does anyone have any issues with the token manager? Or any confusion on how to get there? All right, awesome. Let's go ahead and start installing harpgl. So I'm in section one of the workshop. And like I mentioned before, there's two methods of installing harpgl. One is linking the script bundle into your HTML. Or you have the option of installing the harpgl modules 3MPM. I recommend for this workshop you do the single script tag just for the sake of simplicity. So I'm going to open up my terminal. And I'm going to create a new directory. I'm going to call it harp-map. Let's actually make my terminal a little bit bigger. Is that big enough for everybody? And I'm going to cd into that directory where I'm going to create two files, an index.html and then also an index.js. And the index.js file is where we'll put all of our code for harpgl. Then you can open up that directory with your favorite code editor. So I'll drag that folder into BS code. And then for the HTML, you can go ahead and copy and paste what we have right here into our index.html. And what we're doing here is send up the style, so putting a zero border margin and padding on the website so we don't have any weird borders or scrolling issues. And then also creating a canvas with the ID of a map. So I'm setting that to 100% of the screen with the handy 100 vh and vw. And then we also are adding two script tags from unpackage. One is going to be 3js because we have a dependency on that. And then also the second will be harpgl. And then we also have another script in here called extras.js. That's because there's going to be some extra 3D loading functions that we'll need to add in later on to put in 3D objects. So for this extras file, it's included inside the DevRel workshops resources folder. So you click in there, you'll see that extras.js is right here. You can open the file, click raw, and then just do file save page as into the harp map directory. And then of course we're also linking to our local index.js file where we'll be rewriting the harp code. So now I'll go ahead and start pasting some stuff into index.js. The first is we're going to be selecting the canvas. So just using the DOM get element by ID to select the map. And we'll be passing that into our harp map view constructor. So this just writing canvas is an easier way of saying canvas is the same as canvas. So that might be a little bit easier. And then we're also linking a theme file that is currently hosted on Unpackage. So we have just a nice dark theme. And then we have two other parameters, max physical data source tiles and tile cache size. Those aren't required at first, but they help with some caching to make sure all the tiles aren't reloading when they're in the map view. And the next thing we'll want to do is set the camera location and zoom. So this takes two items in this function. The first we're going to be passing it a geocordinates object. So this is latitude 1.27 and longitude 103. And this is actually the coordinates for Singapore. So it's a format latitude comma longitude. And then also we're setting a zoom level of 16. There's a geospatial standard for zoom levels between 1 and 20, where 20 is when you're really zoomed in. So 20 you'll be able to see the street right in front of you, while 16 is about a nice view to have the city buildings and such visible. If you do zooms one or two, you'll have the whole earth visible. Next, I'm going to paste some map controls. These basically help with the pointer event, so you could drag around the map. Then I'll also add some zoom buttons on the right-hand side. And then I'm also setting a max pitch angle and then also rotation. So since HarpGL is a 3D engine, you could set the angle of what you're viewing. This is between 0 and 90, where 0 is looking straight down. And then 90 would be my point of view. So if you want to set the camera from, say, someone walking or driving on the street to exactly what they'd see, you would use 90. And then also set rotation. This takes the pitch and the rotation. So if you want to rotate the map, this is what you'd use. And then we'll also just include some code to make sure the map changes sizes when you resize the window. And then finally, the most important part is we want to actually add some data to our map. So we're creating an object called an OMV data source. OMV stands for Optimize Map for Visualization, which basically a term we're using for the data to put on the map. Here's where you put the base URL. So as you saw, we just signed up for a service called HereXYZ. We see the XYZ URL here. Then we pass the different API format and then also the style set name. And then finally, you could take that token that you created in the XYZ token manager and paste that into your XYZ token here. So I'm going to go ahead and go back to my token manager, copy this, paste it here. And then to make sure we can see our map, I'm also going to want to set up a simple local server. So Python-m, simple HTTP server, and then your favorite port number. I'm going to use 8888. And then in the browser, we can go to that local host. And we'll see a dark map of Singapore has appeared. Yes, of course. It is bit.ly slash jsconf-harp. And then once you have your map, you could go ahead and drag it around. Also change the pitch and the bearing. I'm doing this with two fingers on my trackpad, moving it up and down. But if you have a mouse or some other sort of trackpad, it's usually right click and drag. Any questions on this step? We'll give it a few minutes and make sure everyone gets their map up and running. Do you guys want to maybe want to walk around, see if there's any questions? So two fingers and drag. You have to, yeah. Any questions over here? Questions? Perfect, it looks like, yeah. Just not as though you have an extra on the JS file. What is the inside there? Yeah, so to download it, first I'll show you where to get it. You mean this one? Yeah, so scroll to the top. And you'll see a folder in here called Resources. So just click on that and download that file. So what this is, is it helps with some 3D object loaders. So some of them are extensions of the 3JS library to import what we call FBX objects. We'll talk about that later on. And then also it is a quick little bug fix that we have for globe controls. We had a release that didn't include it. And we needed it for this workshop. All right. Awesome. You guys having fun rotating your map and moving it around and such? Yeah. Can we share the documentation page for the net controls? Yeah, of course. Yeah, I'll show you guys how to view the documentation as well. So up at the top in the Resources section, we have some links to the repo docs examples. I'm going to click on Docs right here. And that's going to take us to our documentation page. So we have a set of modules out here on the right. With the simple API, these are actually all combined into one. So it may be a little bit tricky to figure out which one you're using with a simple API. But for map view, it's named the same. We could see harp-mapview on the right hand side. We'll click on that. And then inside this module, you could see some of the classes. So there is a class called map view within the module map view. So this is when you'll find all the properties, the getters, and setters, and such for the module. Awesome. So now that we have a map up and running, let's do some modifications to the map programmatically. So in this section, we'll be able to figure out how to change the center in the view. OK. Yeah, that's fine. Bye. I just looked a bit further into this part. But it's not yet so difficult to find. Oh, I think I need to smaller. It's harp.spereprojection. Can you try that harp.spereprojection? Yeah, save that. There you go. OK, sorry. That's a good catch. Nice fix. Same for the next one. That one, actually, that should work fine without the harp. Because did you add the extras.js file? No, over well, just an anti file. Yeah, so scroll up to the top in resources. And then you add the extras. Yeah, so the issue with that is it wasn't added into our build, so we just acted. That's why you don't need the harp. All right, are you guys ready to move on to the new section about modifying the map programmatically? Cool. So yeah, we have a method called set camera location in zoom, which we've already used. And that's where you could set the map to anywhere you want. So if you want to learn how to set the map to your favorite city, you just need to find coordinates for it. So you just type in Seattle coordinates. So really, you just do your favorite city and coordinates. And then there's a nice site here called latlong. And I could just copy and paste this and then paste it into here. And we'll see that the map center will change to whatever city or coordinates you set it to. So I'm from Seattle, so I put the map to here. You also saw that you could change the maxpitch and then also the rotation and the pitch. So based on the maxpitch, what it does is it sets the limit for how far you could change it. So as you see, 90 sometimes doesn't look the best unless you're really zoomed in. If you're out here, the tiles start to cut off. So if you want to limit what the user can actually drag and change it to, you could set the angle there. Usually 45 is a good number to put it to. So we see if we do 45, we cannot go further down than 45 degrees. And also the rotation, you could set here. So we could do maybe 120 degrees. And you could see that the default rotation has changed. So you could set a value there between 0 and 360. Now let's do something fun. First of all, I recommend refreshing the GitHub page because we just found one small bug that was fixed. But if you refresh, everything will work fine. So thanks for bearing with us on that. To change the projection, we're currently at the barricader, say if we want to try the sphere projection. What we'll do is in the construct over map view, for projection, we'll copy and paste this, harp.sphere projection. Let's go up to the top, sphere projection. And then we also need to change the controls a little bit. Since the globe uses a different type of controls, we're going to want to comment out all the current harp.map controls code. That includes also the UI elements and then also the set rotation and max pitch angle. And then we'll want to replace it with the globe controls. Just one thing to note for globe controls, we had to throw that in the extras file. So there's no need to put a harp in front of it. It's just globe controls and then pass the map. And then I'm going to change the default view to zoom level four just so we can see the globe a little bit better. Refresh, oh, new globe controls, excuse me. And now we have a globe view. It's a little bit hard to see because we're in the dark theme. But the next section we'll learn about change of theme and you'll see how to change that. And it'll be a little bit more or a little bit better contrast on the globe. So yeah, just remember to add in a new before the globe controls. So we've created three themes you can include into the harp GL. One is the main earth colors. And then we also have reduced day and nights. These themes are called Berlin, most because the core of the development for harp GL was done in Berlin. And we made some new themes for that. So in order to change the theme, what you could do is pass these URLs into your map view constructor. So if I want to make the theme the Berlin base, I would just go ahead and paste it into theme right up here. So this theme parameter also accepts relative URLs. So if you have a custom theme that you create later on this workshop, it doesn't have to be an HTTPS, absolutely, or a URL. It can just be theme.json because you're referencing a file inside your local directory. So you go ahead and change the theme a couple times. I'll now make the reduced day as reduced night. OK. So do you guys want me to go over the globe part again? Would that be helpful? OK, I'll do that. So now we're back to the normal Mercator flat view. And we'll figure out how to do the globe. So if we go back to the GitHub page for the changing the maps projection section, the first thing we'll want to do in the map constructor is add an option for the projection. So projection is the harp.spear projection. So I'll copy this. I'll go up to the top of my index.js file. And I'll add what I copied in there. So basically what we're setting here is the different type of projection we want. So by default, it goes to the Mercator projection, which is why if we wanted the sphere projection, we have to actually specify that inside the constructor. So that's the first step. The next thing we'll need to do is actually get rid of the current map controls because the map controls only work with Mercator projection. So inside the code that you copy and paste in the very first step of getting the map up and running, we could just go ahead and comment this out. So notice I'm commenting out the harped up map controls basically because the pointer events for interacting with the flat map are slightly different than the globe. I'm also just removing the map controls UI from the side. So since I deleted those, I now need to add different controls for the globe, which I have right here. So const controls equals new globe controls dot map. I want to copy and paste this. And we also made another slight modification of the workshop just two minutes ago. Make sure to add new in front of globe controls. Yeah. Yes. So if some of you guys are having issues with the importing of globe controls, that is coming from the extras.js file. So we had to throw that in last minute due to a small bug. That's also why it doesn't have the harp dot globe controls in there as well. So you could see if you open up extras.js, globe controls is right here. So if you're maybe getting an error, cannot find globe controls, make sure that you have extras.js imported into your HTML. Then once I have that up and running, I can refresh my page and we'll see the globe is working. Any questions over here I can help with? Yeah, those aren't warnings or errors. That's just what's printing out. So no need to worry about those. It's working fine. Is it spiral? Zoom out a lot. Or you could go back to your code and set the zoom level to maybe four. Yep. So you got it working. Nice. Hi. How can I help? Hi. Fields are not currently supported. Globe controls are not defined. So can you show me your code editor, please? Ah, you may. And then you have extras.js. Oh yeah, get rid of the harp dot map controls. Just comment that out. That should fix it. Maybe do a hard cache reset when you refresh. Fields are not currently supported. I think it's maybe have an error with the class inside the extra.js syntax. Do you have a different browser maybe? I'll try that. That's my guess. Is that Firefox isn't reading the class because it's an ES2015 syntax or something. And there you go. That's exactly what it was, I think. Sorry about that. Hi. Sphere projection is not defined. Let's go back to your code. Oh, it's harp dot sphere projection. So right in front of sphere projection. Sorry. Yeah, right there, type harp, h-a-r-p dot. And then save that. And that should work. Perfect. So you want to zoom out a lot to actually see the globe. Nice. It's working. You guys doing OK over here? I'm good. Yeah, I'm good. Oh, I'm sorry. Scroll to the very top of this repo. And it's in the resources file. Yeah, sorry, that was a little confusing. That's good. Yeah, for those of you who already got the globe running, try to maybe change the map theme and such, play around with that. And we'll resume in a minute or so. Unexpected token. So interesting. Let's take a look at your extras.js file. This is extras. I think this, oh, I think what happened is you downloaded the GitHub HTML instead of, yeah. I need to click it. Are you guys doing OK over here? Yeah. OK. Just click it. All right. Yeah, that should work. Any questions over here I could help with? That's a classic. Perfect. He is following me everywhere I go. No. Because the theme is fine. The what? Changing the theme. The theme, yeah. So to change the theme, well, first of all, we have three default themes you could use. Base, reduce day and night. So we have links to all three of those files right here. If you click on them, they're all JSON files. And you could set the theme in the constructor. So if I want to do the reduce day, I could copy this link and then go into my constructor and this theme parameter right here. I can copy and paste the absolute URL to it. So I'll set it to dark. I'm sorry, night here. I don't know. Yeah, it is night. And then I could go to my web app, just refresh. And you'll see that it's changed to dark. So you could change the theme in the map view constructor. There's also the option to set the theme programmatically later on outside the constructor. And you could just copy and paste this code to do it as well. It's right below the three different maps on the GitHub page. For this next step, let's do something fun. Let's add a rotating camera around the map to create an effect like this, where the map's rotating automatically. So to do so, it's pretty simple. Just copy and paste a couple lines of code. But what we'll be using is a method called map.lookat. It's very similar to set camera geolocation zoom. However, this time you can pass it more than just the zoom level and coordinates. You could also pass it the tilt and the rotation. So I'll copy and paste this into my index.js. Yes, that's actually a great point. So if we're going to do the rotation, we should actually move away from the globe. So we'll go back to the map controls. So to do so, we're going to get rid of this projection in the constructor. And then add our map controls back to the map and get rid of the globe controls. So this way, we're going to go back to the flat map. So make sure to go to the flat map if you want to do the animation that we're about to do. So for the rotation code, we're basically waiting for a map event, saying that the map has rendered. And that means we want to then fire off the rotation. So every time it renders, we're going to want to update the rotation, so the azimuth right here. And then we'll use a piece of code that just begins the animation with map.begin animation. So if we go back and refresh our screen, we'll see the rotating view of Singapore. I'm actually going to go back and update the theme to the base style just so there's a little bit more contrast on the buildings. There we go. So this is a pretty fun view to have your map set at. Very game-like. And you don't have to set it to the Singapore coordinates. You could also set the rotation to whatever city you come from or your favorite city as well. And so feel free to play around with the rotation, the center, and such for five or so minutes. And then we'll resume on to the next section. Any questions? Yes? I think we're just for an infinite year. We want to start right. Yeah, infinite. So basically, if you look at the code, every time the map renders, which is basically multiple times per second, we're adding some of the angle here. So as long as the map is rendering, which it always will be, it will continue. Do you know how we can stop it after this? Can we set a timeout? You could. So you could say maybe do a while loop that's adding up. So yeah, you could use a set timeout, a set interval, a while loop, really any other sort of design. Yes? OK. Correct. Hi, anything I can help with over here? Yeah, can you explain? I think I get it. I need to explain it. But can you explain how, like, why, what exactly this is? Yeah, so the azimuth is basically the angle between 0 and 360. And so we have this event here called Render. And that's basically firing multiple times per second. And every time it's rendering, we're basically adding a little bit to the angle. That's why it's changing. So yeah, if you want to increase the velocity, you would just add a higher angle or something like that. And then if you want to make it slower, just make it 0.01 or something like that. OK, so now I just want to show you. Oh my god, that's going to go crazy. I want to see it. Oh, it might not even go anywhere. Yeah, because 360. Right. Oh my god, this is going to make me sick, I bet. Just like motion sickness. Oh, actually not that much. Yeah, I guess think about it. I guess if it's between 0 and 180, that's the only thing it's going to do, yeah. I just want this to go super fast. There we go. Not going to work. Nice. I wonder why the beautiful view of the city. I probably can't handle it. What angle did you set? 179. Oh, 300 plus. Yeah, I don't know. Interesting. Anyways, thank you. Yeah, no worries. Anything I could help with over here? What did you start with? Yeah, so even setting it to 3 makes it go super fast. And yeah, 5 is way too much, I think. You guys having fun? Cool. All right, are you guys ready to move on to the next section? So now that we've got the map set up, you've learned how to rotate the camera, change the theme to default themes, as well as set the center and the pitch and such. Let's do something fun, which is styling the base map. So since HarpGL is a vector render, you could really go crazy with styling the map and do any of those style rules that you want that we kind of talked about in the beginning. Like C, for example, I just made all the buildings green and yellow. The road's purple. I mean, yes, it's ugly as hell, but it's kind of fun to just be able to create this type of stuff. So we have a JSON editor that you can do to edit these styles. Right here in the section 3 styling the base map, you'll see a link to heremaps.github.io slash harp dash map dash editor. You go ahead and click on this, and you could think of this kind of as an interactive prototype and environment for styling maps. Yes, it is all in code, technically, just JSON. There's not really a UI to be changing the colors. But still, it's nice because you could actually see the changes live in the screen to the right without having to refresh your page or anything. So what we have here are all the different style rules. Up here, we kind of have some globals around lights and fogs and textiles and such. But down at around line 79, you actually see some of the styles. This is the same syntax we talked about in the beginning. So say, for example, if you want to see the piers, you could actually change the color of the piers and such. And this style file might be a little bit overwhelming because there's a couple of thousand lines along. That's because we have every single map element inside of here. So really, the main things that you might want to edit would be, say, like the Earth background. You could search for Earth in here. You might want to also change water. So we could change the fill to maybe just yellow. My goal right here is to make the ugliest map possible. Let's see what I could do. So yellow water, that's kind of crazy right now. Let's change the Earth to maybe white background. Can I ask you any reason why Earth isn't working? I'm editing the text here, I see. You're only doing the animals. Oh, I see. That's for sure if the island will affect it. Maybe this is a pattern that doesn't remove the whole condition just later. Now, these are both text. Actually, what is the background layer? In this case, you need to zoom out to see the background. All of these are. Oh, is this land? Yeah, it should be land use and land. Nothing can change. You can do color pick if you want. There we go. Yeah, so Earth is actually just the background. It's not the land. Land is actually called land. And we actually have a couple different types of land, like urban and parkland. But actually, white does not look too good. I think I'm going to go back to the previous color. But a fun one to change and customize, especially in the context of the 3D engine, are buildings. So if you actually scroll down to the very bottom, you'll see Building Geometry. It's line 1800. And this is where you could start changing some of the things for buildings. So we could do a background of blue for a building. You could see now we have the blue background with the teal outline. But maybe let's make this a red outline. Yeah, this is pretty ugly so far. And then you could also style roads. Roads are generally classified into three high level categories of primary, secondary, and tertiary. So if I want to do primary roads, I'm going to search for primary in here. And then you could change the color. What colors have I not used? Let's do green. Yep, and then you could see some of the highways are now green. Now I'm going to search for secondary. Make the secondary colors whites. Give some contrast to that. There you go. And then for the third tier of roads, tertiary. Any colors you guys want to see me add? Any suggestions? Do we have a question from the audience from Nina? What color? Purple. Nice. Yeah, so there's a lot going on with this map. But anyway, knock yourself out with the colors there. But once you're done creating this hideous style, or maybe some of you guys have created a beautiful style, you could actually click this download button in the middle sidebar. So I'll download that file. By default, it went to my downloads. But what I could do is actually drag that into my folder directory. So mine was called heart map. I'm going to rename it just theme.json instead of theme space parentheses 1. And then I could go back to my code and then inside the theme option right here. Instead of doing the absolute URL to the here map theme, I could just do theme.json. Because I'm referencing the local file that I just downloaded from the heart editor. And when I go to my map and I refresh, you're going to see this hideous theme in your own map. So I'll fix the tilt a little bit. So just to repeat that process, in case anyone missed it, inside the heart map editor, you see this button right here. It's the download, the down arrow. You can click on that. And then it will basically download this JSON file in the left-hand side. And then you could put that inside your project directory and then reference it in the map view constructor to set the theme. Any questions over here? I'm done with the last step, so that's it for 2.2, OK? Yeah, did you put the dancing guy? No, I skipped it. That's OK. Yeah, if you did all the steps, you've completed the workshop. So if you want, you're free to leave. Or if you have any other questions, I'd be happy to help. No, it's all up to the particular show. Awesome. More of a configuration. Yeah. And get to know all the details. The different APIs and stuff. Yeah. Well, I'm glad you enjoyed it. Are you going to put it into any projects you've been working on recently? Not now yet, but I hope I'll check. Awesome. Well, thanks for attending. Cool, thanks. Nice to meet you. What was your name? Dylan. Dylan, hi. For the style, if somebody wants to look into that, there's the layers definition, but you can see the specification of exactly what they see in each one. You know what you wanted to do before you changed the background of the art? Yeah, but where is it? It's on there. I suppose you can have the type of style. So you can go there and check it out. Because we use types and specifications. I don't know if you want to go into that later. Yeah, I think it's going to be a little more complicated. All right, I hope you all are having fun with the map styles and knocking yourself out, creating some crazy styles. Let's move on to the next section of adding data to the map. So these maps are really fun and awesome, making the colors all pretty and stuff. But we could actually add some utility to them and create some data visualizations of geographic data. So before we move on to the next section, I'm just going to go ahead and disable this animation that we have running, mostly because it doesn't let you control the map if it's currently running. And then I'm also going to set my zoom level to something a little bit further down so we can actually see Singapore. So basically just going to reset my map to the Singapore coordinates as well. Now it's looking a little bit better to where we had the map before. So the first exercise we'll do is add some GeoJSON to the map and we'll be adding static GeoJSON. So it's not going to be coming from a server and it's not going to be already be tiled. We'll simply just be adding a GeoJSON file we have locally on our machine onto the map. And so inside the resources directory of this repository, we have a file in here called wireless-hotspots.geojson. So what this is is basically a list of all the public hotspots for Wi-Fi throughout Singapore. And so I'll go ahead and just download this file. So download and then save page as. And then wireless-hotspots.geojson. By default, GitHub is putting a .txt to the end of the file. You want to go ahead and remove that so the file extension is .geojson. And I'm going to want to save that into my project directory. So I could go back to my VS Code Editor and actually take a look at the data in here. It's GeoJSON, the same as what we learned earlier in this workshop of you see the properties, which has some HTML in here as a string. But then also near the end, let's scroll past this, you'll actually see the geometry in here. So we see that it's type point. And then we have the coordinates right here. So basically giving us the information of where to put this dot on the map. And I'll go back to the readme file where I'll copy some of the code. So what we'll be doing here is creating a network request using the fetch function to the wireless-hotspots.geojson file. Just to make sure that works, let's do a console.log of the data. Just make sure we see it over here. Yep, so it looks like that request is successful. We see all the different features in here from the file, the properties and such. So the first thing we want to do is create a GeoJSON data provider. So you could use the function harp.geojson data provider, pass it the name, which will be wireless-hotspots. And then you also want to pass it the variable of the data. So I just named it data. Then once you've created the GeoJSON data provider, you'll want to create a GeoJSON data source. So with this, you also pass the two parameters, the data provider we just created, so GeoJSON data provider, and then wireless-hotspots. So this code will technically add it to the map. We need to do one more function, map.addDataSource, GeoJSON data source. But we need to do one more thing once it's added to the map. We need to apply the styles in order for the data to show. So we could add it to the map, but if there's no styles provided to the map, it won't have anything to show the data. It would just be blank objects on the map. So what we're doing is passing one of these style objects. These are the same style objects that are within the theme.json file, except we're just doing it within a JavaScript now. So we're saying when geometry type is a point, we're going to want to use the circles technique and then style it this color. Then once we've created that object, we'll want to pass it to the GeoJSON data source using the function setStyleSet. And then we will call map.update. So once we have that paste in here, we can go back to our map, refresh. And although we have a ton of different colors on the map right now, you can see these kind of light green highlighter colors are all the GeoJSON points that we added. So every time you see a teal, I'm sorry, not teal, highlighter color, these are the wireless hotspots within Singapore. And so if I wanted to change the color of those hotspots, I could edit it right here in my JavaScript. So we could do white this time for a little bit more contrast. That definitely looks a little bit better. And so if your map is not showing the data or if you're not within Singapore, you should make sure to set your coordinates back to Singapore so you'll be able to actually see the data on the map. How are you doing over here? Awesome. Well, let me know if there's anything I could help with. Any questions over here? So are you developing on an iPad? Yeah. At school, you have windows running on here? We have more windows. That's awesome. How to change the what? Oh, the tilt. So you do it with your mouse like that. But to do it with the code, go back to your VS code. Scroll up. And you want to do set rotation. So 50 is the current set. So you can do maybe just zero if you want to top down view. There you go. Any questions over here? So you guys just learned how to add static GeoJSON from a file onto the map. But there's also different types of data sources you could add, such as tiled data sources from servers. So we have another product called HereXYZ, which basically does tiled data sources for you. Which that means is when you have large data sets, you want to actually divide it up into squares across the world. Basically what this means is you don't have to load all the data at once. So if you had a 10 gigabyte file of the Earth, you really only want to render the file that you're seeing in the viewport. So say, for example, if we were looking at Singapore, what XYZ would do is actually query the data just for your viewport. So that's basically what a tiled data source is. So in this next exercise, we're going to actually want to add a tiled data source. And to do so, we've already set up a data source for you. It's going to be global railroads all across the world. And to do this, you'll want to actually use another harp.omv data source. So right here in the section adding tiled geojson from the server, we'll want to copy and paste this global railroads variable. And what this is, is the base URL to this data set. We'd see the unique identifier right here. You don't really have to think too much about this API endpoint. This is just where the data is stored. However, something that is important is this authentication code. Previously, when you added the base map data, when you created the map, you passed your own authentication code. It's important to use this authentication code provided in the code, because that basically gives you access to the data set. Do not put your own authentication code inside of here. So once I've created the OMB data source, I then want to add it to the map. So I'll be using the same syntax that I did before for the static geojson. Basically, instead of referencing a file that I've added to my site, I'm now referencing this tiled data source from a server. So I'll do the same function, map.addDataSource. This time, I'm just doing global railroads instead of the geojson data source. And then I'm attaching the style to it. This time, the global railroads are line set of points. So I have, when geometry type is line, we're going to want to use this technique. Solid line with this color. And then it's always going to be one pixel wide. So beforehand, and you could also do options for circles or lines in meters. The difference with one pixel is that the size will say constant no matter what zoom you're at. Next, we'll attach the style set to the global railroads, and then we'll update the map. Also, because this is a global data set, I'm going to want to change my zoom level to maybe, say, four or five so I can see the entire data set. Then also fix this rotation. Here we go. So it does take a little bit longer because it's a much larger service and file. But you now should see red lines pop up all over the globe. You see India has a lot. Europe is pretty populated as well. These are all the railroads in the entire world. You actually see these are loading kind of square by square. Those are the tiles I was just mentioning. So when the viewport sees that we are looking at this, it's not going to load up this tile of the data set. So this is actually a pretty data visualization. Just lines all over the place, although I don't know if the red looks too good with my teal background. Yeah, of course. Yeah, so we didn't go too much into detail on the X, Y, Z part, but that's basically a back-end server that's taking the data when you upload it, basically dividing up the tiles all over the globe. And so what HarpGL is doing is when you add that data source, it takes basically the viewport coordinates that you're looking at. So say Singapore, it's taking those coordinates, and also the zoom level, and it's sending the query back to the server to only ask for that data. That way, you're not loading everything at once. But I guess it's a little bit different when you look at the world, because we're calling all the tiles. But it's a little bit more efficient if you're just loading a smaller zoom level area. So the part, like the X, Y, Z portion that like? Yeah, so that's another product. It's technically open source as well. You can find that in GitHub and such, but we're just not going into too much detail. We're mostly just doing the visualization side of thing. But if you're in a lot of geospatial data engineering, that's actually a very helpful tool. So I believe the API, I'm sorry, the endpoint is like explore.xyz.here.com. So just type in here, XYZ, you get some more information on the product. And they also have a map styling studio. You can do pretty much the same things as this, but all with a UI, so you don't have to actually code it. So pros and cons, obviously with HarpGL, since you can code with it, you can really get any styles really. There's no limits on what you can do. Whereas the UI, it's a little bit more basic for non-coders, where there's a little bit limitations on it. So it really depends on what type of project you're doing. How's it going over here? Everyone's excited. Nice. Awesome, so our map is looking great by now when we put all the railroad colors and lines on here. Sorry, not colors, just lines. But there's also a concept called data-driven styling, which you basically styled the data based on different properties. So right now, all the lines are just one color, because they're all the different railroads in here. But say if we wanted to see the different railroads that are not active or that are currently shut down, what we could do is take the property from the GeoJSON and the tiles that says railroads are not active or they're closed and such, and apply different colors to those. That way we'd get a mix of maybe red lines for active railroads and then a different color for railroads that are closed. Say if we were some sort of data analyst and we wanted to see which countries had closed railroads and stuff like that. So you could apply different styling rules to the properties of the data. To do so, we don't have to change any of the code for adding the data source and such. All we have to do is change the style rules that we applied. So I'm going to go to the code block where I added a style, and I'm going to replace it right here, just delete that, with two new style objects. Previously we had when geometry type equals a line, we apply a rule, but now we're adding something else. We're going to say when geometry type is a line, and properties.status is open. So what this properties and status is, is if we go back to the GeoJSON, this is just an example of how it looks, we see in properties there is a key in value pair that says status is open. So we want to select that data and apply this color, the 50E3C2. And then we also have when properties are either closed or we don't know. So we'll assume those are closed. We could then apply a different color. We could do this D6306. So basically we're splitting the data into two different buckets here, open or closed or possibly unknown. So we could save that file, go back to our web app, let it load, and the colors that I set is green or teal equals active, and then red is closed. So you could see there's some red lines that are now popping up in South America and also Africa. And that means that the railroads are closed. So you could apply these techniques to really any data set to differentiate between different properties. Say for the Singapore data set we could have done maybe the size of the circle depending on how many devices it can handle at once and such. Really any sort of property in the data, quantitative or qualitative, you could add to the styling rules on the map. I probably have been standing in front of it. Just the back of your shirt. That's fine. Oh, how to remove them? Yeah, so you do that in your theme file. So right now you are, let's see, you're calling a theme you can edit. What you do is you would open that up inside the map to the editor. And then, so what I did is. Yeah, so there's a quick little hack you could do instead of deleting all the text. What you could do is just download this file. And basically, this has dependencies on other resource files, like font files and icons. So if you download that and you just add it to your theme, the fonts or the text won't show up because the attached fonts aren't available in the same way that the URL would have them. All right, any questions on the data driven styles? Are you all ready to move on to 3D objects? Yeah? There we go. That's the excitement I'd like to see. Cool. So because HarpGL is built on a popular 3D web library called 3JS, you're actually able to call all the APIs that you would a 3JS right inside of Harp as well. So for a little bit more information on 3JS, you could click on their site. They have a lot of cool examples of things you could do with 3JS. It's a fun little gallery to look through. But the first exercise we'll be doing is adding a simple cube to the map, something just like this. This isn't really a geographic object or anything like this, we're just simply creating a 3D cube with the 3JS APIs and then adding it to the map. So what I'll do is copy this, go to my index.js. And this is all 3JS code, which I'm not exactly too familiar with, but we'll be creating the geometry. So size 100 on all the edges, and then adding some material, which will simply just be a pink color, and then creating the cube with the geometry and material. We're also doing a property called renderOrder. This is basically the Z index for all the objects on the map, just to make sure this shows up above buildings and roads and such. Next we'll be assigning a geo position. And then we will be adding it to the map with map.map, anchors.ads, cube. So the logic I want to set up is that wherever I click on the map, I want to be able to add a cube. So we'll be adding an event listener, just canvas.onclick. So basically when the map canvas is clicked, we're going to want to create this object and add it to the map. So since I'm already zoomed out pretty far, because I was showing the whole world, and we're going to be creating a pretty small cube, before I execute this code, I'm going to want to change my zoom level to something a little bit larger so we can actually see the cube. So I'm going to go back to maybe 16 or 17. I'll go and refresh my page. I'm back to Singapore. And now whenever I click, we'll see a cube is popping up. And it's a nice 3D cube. Basically the event listener is saying, when clicked, I want to view the coordinates of the click. And then I'm going to assign those coordinates to the cube position. And then I'm going to add it to the map. So really you could honestly create like a game of checkers here if you wanted to by assigning the different colors on alternate clicks and such. Or you could also make massive cubes by changing the box geometry size. Let's increase it by 100 times. And you see if we clicked on it, we basically crushed the entire city on accident. Yeah, so we have quite the ridiculous map going on here. Teal water, cubes everywhere, railroad showing, and still wireless hotspots as well. As you see, you could really go crazy with these maps if you want to. All right, so now that we added the cube, the cube's a little boring, you have to admit. How about we add a dancing 3D man like this? That's a little bit more exciting of a 3G object, huh? So we created the previous cube just programmatically using the 3JS APIs. But this time we're going to be importing an object into our map. So if we go into the resources file of this repository, we'll want to download this dancing.fbx. This is a 3D object. So I click Download. And then I'll go ahead and move it into my project folder. And I'm going to get rid of the parentheses 1. So before we proceed, just make sure you've downloaded this dancing.fbx 3D object into your project directory. And it's available inside the resources folder. So in order to add this to the map, I'll go ahead and copy and paste the code added in there. We're going to be using a 3JS, what is called an FBX loader. So this is basically making a network request to get this file dancing.fbx and then basically parsing it so we can use it in our 3D scene. We'll be doing some actions like setting the render order so that it's high up on the map and it's not behind anything. Then also doing, it's like setting the scale to make it as large as we want and then just setting a name to it. So we can name it human or you can name it whatever you want. And then also we're going to set the geo position. So we're just going to set it somewhere in Singapore using the harp.geo coordinates API. And then finally, we will do the same thing as we did before, map.map anchors.add object. So this will add it to the map. But because we have an animated object, we also need to make it animate. So add a little bit more code. We'll be doing the same event listener as before for the map rotation. Actually, no, it's not the same one. It's similar, though. MapView eventNames.render. And then basically if the object is loaded, we're going to want to set it to animate. So once we pasted this code, we could go back to our map and then we should have our dancing man somewhere. Here he is. He's over in the water. So here he is. He's dancing right next to the Marina Bay sands. I'm actually going to set my max pitch to something a little bit higher, to 90 so we get a better angle. There he is. So he's having fun dancing away. He loves JSConf so much that he's expressing his happiness. So this is just an example object that we found on the 3JS site. You could really do this with any 3JS object that you have. So if you have some other fun dancing people, or really something like a spaceship taking off, you could easily add this to the map using the same code as before. So any questions on the dancing person I could help with? That was very cool. All right, everybody. So we're almost done with the workshop. That was the second to last final activity. So you guys have all made some pretty cool maps by now. You have dancing people on them. You have cubes all over the place. Wireless hotspots, railroads, and probably really strange watercolor, just like mine. So I encourage you to actually share these maps with us from the workshop. So since we have the simple API, your files right now are usually just index.html, index.js, any of the dancing person in your theme. We recommend you guys create a new GitHub repository and set up GitHub pages so you can actually create a URL to your project. Then feel free to tweet at us. We are at here dev, and we'll be retweeting some of our favorite maps. It's definitely a good way to be able to show your friends and family what you did at JSConf. You'd say, hey, I made this awesome 3D map with some really strange colors and dancing people on top. Definitely a good thing to show people. So do you all know how to make a GitHub pages website, or should I go through that? I think I'll go ahead and do that. So to create a GitHub pages account, you could go to github.com, and then go to the top right, C little plus, click New Repository. And I'm going to say, I'm going to title this My Awesome Map. And the description could be made during the HarpGL workshop. Click Create a Repository. And I'm going to go back to my command line inside the directory that my project is. And I'm going to create a new Git repository. So Git init. And then I'm going to add everything in here. So Git add. And then Git commit-m, first commit of My Awesome Map. And I want to add the remote of this GitHub page repository. And then push everything with Git push origin master. So if we give it a sec, we'll see that all the files have popped up in here. Even my DS store, that shouldn't be committed. And then inside the Settings tab, you could go scroll down until you see GitHub pages. And then you'll set the source to master branch. That will save automatically. And the page will take one or two minutes to build. So we'll check back then. And we'll see how the website's looking. But the URL will be your GitHub username. So mine is dbabs.github.io. And then the name of the repository. So mine is called my-awesome-map. Oh, and it's already built. And we'll see the same map we had as before. See, I think we're just a little bit zoomed in. We have some errors there. There we go. The map was just wasn't loaded in the first try. And now we have a shareable link to the map we just built. So you go ahead and tweet that. We are on Twitter at here dev. So thank you all for attending this workshop. We hope you've had fun and learned a lot about HARPGL. So far, you've learned how to create a new HARPGL application from scratch. You've learned how to customize the theme, add data to the map, as well as style that data with data-driven styling. And then you've also learned how to add 3D objects to the map. So if you have any feedback on the workshop or on HARPGL, we're always looking for improvement. You could fill out this Google Form we have set up. The team will be reviewing everything. Or you could also create an issue on the HARPGL GitHub repository. So thank you very much. And feel free to stick around as long as you want and continue working on the maps. And we'll be continuing to provide support or answering any questions.