3D slippy map with three.js
CC Attribution 3.0 Germany:
You are free to use, adapt and copy, distribute and transmit the work or content in adapted or unchanged form for any legal purpose as long as the work is attributed to the author in the manner specified by the author or licensor.
Pedersen, Jarle Johan
We will demonstrate the use of WMS and WCS as input to three.js for rendering an interactive 3D-model in the browser, based on actual data. Our extension of three.js, (WxS.threejs) takes several inputs, the boundingbox being the simplest. WMS-service, WCS-service, LAYERS and many, many other variables can be set either via the URL or predefined in a quick and easy setup. Further, we wish to introduce the idea of using cached WMS as an input. We've prepared a framework that is ready for consuming WMTS, rendering tiled 3D-models that are stitched together. The goal is to implement a slippy map in 3D. This is an open invitation to all hungry hackers who wish to join us in tapping the potential.Original article:-i-threejs/Example:
 All right, I think we're there. Hi everyone, my name is Yara Pellusen. I come from the Norwegian mapping authorities where I worked the last six years. My background is mainly within post-GIS work, backend stuff, some configuring of services, stuff like that. So me venturing into the world of 3JS and JavaScript in general has been a, let's call it a learning experience. So what I'm going to present today is the state of this projects mine, WXS.3JS, which is basically trying to visualize, make a 3D map based on services, WCS services, and initially WMS services, eventually also cached WMTS services. And the end product will be, is not, will be a sleepy map, the one we know from open layers, etc. So now that they closed the door, we could probably just start, I guess. All right, so no good presentation without an overview. We start off with just like the history background of the project, how it came to be. Then I will just go into the components that are part of the project right now, give a brief overview of those. Then since this is a visual project, I'm just going to go straight into the demo. I will use some time on GitHub, just looking to the code, showing everywhere, everyone where stuff is, and also hopefully I will be able to do a couple of live demos, knock on wood. So yeah, I'm going to try to summarize afterwards by going through a good, bad, ugly, and also try to sketch out the future, as I see it, and end up with a summary. For those of you who read the description of this talk, you will have noticed that I'm actually looking for developers. It would be really cool. But, and also the, I should mention that the project is a MIT licensed, so you're free to basically do whatever you want with it, if you find it, find it to your liking. All right, so the history. The idea came about, I was attending a hackathon in Norway with the like cultural ministry, which I was there representing the national mapping authorities, trying to educate people on how to use our data in their products. And being in such an environment, you tend to get, well, inspired really, because there's a lot of people around you, they're all hacking, they're all got their ideas. And I, sitting there, I remembered reading this blog. This guy, Björn Sönlik, wrote this blog post on how he basically took a digital elevation model and married it with 3JS to create this. I thought, wow, that's really cool. I want to do that. Then I took a, I figured, well, since I work with services mainly, that's my main job, that's what I do, I create services. And for a long time, the longest time we had this WCS service, which I don't know, is everyone familiar with WCS? Is that, oh, sorry, is anyone not familiar with WCS? Everyone? Okay. WCS is a raster-based, it delivers rasters, it's like WMS, except you get the data instead of just a picture. So I made this WCS service. The problem was no one was using it. So this would be a really good idea to sort of show off the service and maybe show how you can use, utilize the WCS service on the fly, et cetera. So I started out. Let me just go straight into this one as well. First thing I noticed was there was a disjoint between WCS, or the formats that WCS wants to give you. Basically, I only had it configured for GeoTiffs. Turns out browsers don't like Tiff files. They don't want to have anything to do with that. So that was a problem. So I could order the elevations, I got them, but I couldn't do anything with them. So, okay, well, figure, let's hack around that. So I set up the WCS so that I now can give XYZ files. That's fine and dandy. So now I get the elevations. And now all I had to do was plug in the WMS get URL. And basically what I ended up with there was, oops, let's see, it's better from this perspective, 3D model like that, which is created based on nothing but a bounding box, really. Give it a bounding box. It's going to query the WCS, it queries the WMS, and it meshes it together and wham bam, 3JS. Brilliant tool, really. So, yeah. For those of you who haven't used 3JS, I would suggest going to this place just to need to plug there. It's a wealth of inspiration in there. I will not go into the details of each of them. Just know that it's there. Okay, presentation, presentation. All right. So for the components. All right. It's very easy and it's very lightweight. The project has only been around for like six months. The code base is 1,000 lines. So I'm trying to keep it simple. But we need, of course, obviously we need 3JS for the visualization. After long last, I did find this TIFFJS, which enabled me to get around the problem of using the XYZ files. XYZ files is very, very big. I mean, you get, it's basically text files. So it's not compressed at all. So it takes a while to get the data. Using TIFFJS, I was able to read the TIFF files from the WCS. Brilliant little piece of JavaScript in there. Some limitations to it. I so far, I haven't been able to get an array of length larger than 2048. But I'm sure that eventually we'll get through that as well. Services initially, we use WMS and WCS. And again, for those who read the description of this talk, it says that we're planning to do WMTS. Yay! Actually, we do now. The current code will use WMTS, it uses tiles. There are some problems with it. And as much as I sort of broke the WMS implementation, so now you need to have a tile set. But it works as long as you're in Norway. But it's not a problem. You just, if you plug in another tile set, it should work out of the box. And it is easy to fix. I've just been sort of busy doing other stuff. Aren't we all? So demo-wise, first, oh, no, no, no, you weren't supposed to see that. Okay, so get up page. We are three people who committed to do the project so far. You can tell that this part over here was the initial, when we initially did it, you'll find that this is the vacation. And then this is me getting nervous before this talk. But there's been, like I said, it's not very six months old. There is a total of a thousand lines of code, about 80 commits in total. So fairly young. The structure is, again, quite basic. Got your external libraries here, get your source code in here. I'm just going to go briefly through the organization of this because, oh, yeah, I didn't mention. None of this is documented. The page where I show you the labs.CardFerke.no page has some documentation of the parameters that it takes. You can parameterize it using SRS or like coordinate system projections or you can use your own WCS in the URL, which layers are you using, what coverage are you using, stuff like that. It's in the article. But the best place is actually this part. Fairly simple, really. This thing here checks in the URL you're using to see if any of these keywords are there. Fetch its value and assigns it to the variable. Then it's reused throughout. What else is I said? I was saying this wasn't documented. This is documented. All right. So that was the universe part of it. This one everyone should ignore because it's not there, really. So then you have the WCS and WMTS loaders, really. What they do is they basically enable you. The WCS here takes a TIFF file and would basically iterate through a geometry, a TIFF, sorry, a 3JS geometry and assign the Z values to the corresponding vertices throughout. The meat of the project is in this file. It is not very big, but it's the thing that sort of tries to sew everything together. It is where you will find it. It will sort out what the different bounding boxes are. It will fetch the tiles and, well, it's where everything happens. It's a big factory. If you ever tried to use this, this is probably where you will start scratching your head and say, what on earth is going on here? Yes. So now is when I show you the pretty pictures and pray to the techno gods. Let's start with this one. This is the standard area that I use for testing purposes. So basically, we have your 3D model right here. In this case, I preloaded this because I don't, but it should load fairly quickly. Notice also that this is using a WMS. That was, now let's try the sleepy part. Hopefully this works because in theory, yeah, here we go. That was a bit scary. So I'm going to try to refresh this page since it seemed to work. Notice also in the URL, you have a bounding box up here. You have a layer defined at the end. And now it doesn't load. Yeah. Look at that. Luckily, I have another demo to show. I figured I'd just show off how you can use, this is just my example implementation. You can make much more fancy. I'm not a designer. So if you're a designer, you probably have a, you probably like get your head down in your lap right now, scratching your eyeballs out or something. But the idea here being that you define a bounding box over here and, God, this really, I hope this works. And what you're not seeing right now is the 3D model appearing where it should be. Yeah, yeah, oh, I forgot. I forgot. I forgot. Of course, it's nighttime. Yeah. Yeah. That was too bad. That was going to be the big piece de resistance. Look at that. While you're not looking. So the next thing I was going to show that was supposed to go really fast is you can change your layers over here and you click the button and it's nighttime again. Yeah, okay. I swear this works. Anyway, that sucks. Oh, okay. Excellent. Okay. So, yeah, okay. So here you have your 3D. See, this is really fancy when it works but what a downer. I swear it's faster when, but right now I know this is from a server in Norway and probably the network here isn't. Yeah, I'm playing the network. Okay. So you're all seeing it work. That's great. I'm not going to try any more demos. So we jump to the good, bad, and ugly. So the good stuff is it is, should be, fairly easy to use for when it's set up properly. The fact that you can just define your parameters in the URL makes it easy to just construct your URL and then you bang, you get your 3D model up and running. I also listed the potential there. Seeing as, to my mind, it does have a lot of potential. I know there are people out there who make much more fancy graphics and they make their globes and everything is looking really nice. This does one thing and hopefully it should do it really well. I listed a few bugs. Colbeys of a thousand lines. There's a limit to how many bugs you can get. It does still have some do pop up now and then but so bad stuff. Well, low maturity, that's a given. But I find that it's really rewarding to work with it because there's still so many things to do. So you can actually work on something. You don't nitpick on a small bug that no one's ever going to notice. You can actually make new features in this. There's no projections. That's part of the keeping it simple. Right now, you sort of have to use the same projection on your WCS as your, whatever you're overlaying, WMS, WMTS. And yes, as I mentioned earlier, the lack of documentation can be an issue. Ugly. Yes, some of the code is ugly. Particularly the part when I just, I think the latest commit I did tried to average values in the corners between tiles. That's not easy and I have no idea. I'm not sure that I even can understand the code myself right now. So hopefully someone will make it more legible at some point. I got to the point where it worked and then it was hands off. Clunky navigation. Yes, so far I haven't done anything to the navigation. Just use the standard one that I found in an example somewhere. And that is a big one that should be fixed. It is a big piece of work getting that because it ties into a lot of other things. Like if you want this to be a true slip map, you want to be able to do, you need to be able to change some levels and stuff like that. And that ties into navigation of the camera. So it's a big piece of work that needs doing. Yeah. And as I mentioned earlier, right now it's sort of a hard code to use WMTS. It could be fixed fairly easy but it's going to be ugly because if you try to use this and you're sort of outside of Norway, it might break entirely. Yeah. So it brings us to the future of this. I imagine, well, these three things, two of them, the first two should be doable in my lifetime. Changing zoom levels dynamically. Right now it doesn't do that at all. You get the zoom level that sort of corresponds to the initial bounding box you start with and that's what you're stuck with. But there is some considerations taking to account there with like level of details because, you know, the classic way of doing this is that you have higher resolution tiles close to where you're looking from and then you have lower resolution tiles further away. The problem is that then you then query different zoom levels and if you have different generalization, it tends to start looking ugly quite quick. It's my experience anyway. Of course, the other way to do it is to create a, to tailor WMTS and WMS service for the specific use but then that wouldn't be general enough. I want something more general than that. So I haven't really tackled that problem yet. All right, optimizing geometry. Yes, big one. Right now we load tiles, we load geometry and we just sort of stack them together, do a little bit of edge trying to sort them together along the edges, not much more than that. I have read documentation on how to merge it. Still haven't really gone into that one, particularly because I haven't figured out whether or not we're going to reuse the geometry or just get some new geometry. All right, those are the two ways to go. No idea which one is the better. Still, I'm fairly optimistic that changing zoom levels and optimizing geometry should be quite possible to do quite soon, which brings me to the third one, the WFS. Yeah. I imagine the first one, importing geo-json could be done. I mean, there must be libraries out there. You can read geo-json from WFS and then sort of mapping those up to 3JS and its geometry types should be fairly easy. GML, I'm not as certain. Well, I put it up there because it is an interesting problem that could be tackled. So, yeah, just put this one together so everyone wants to take a picture. This is the information you need. And I'm just going to wrap it up there. Thank you. Does the fact that we really just need 2.5D help the ability to do the navigation, the slippy part, so we can get rid of the pivoting part? And then that makes it easier to just navigate kind of up and down and forward and back, side to side. Yes. Yes. I thought I should probably make that distinction earlier on because someone was bound to point out that it's not 3D, it's 2.5D. But, yeah, that is basically what I'm leveraging right now. Do you do any level of detail rendering with the trains or do you have any plans for really large landscapes? That's the thing I really haven't figured out how to do yet. I mean, the geometry is easy. But getting the graphics to tie together, that's the problem. I mean, I've asked several people about this and some of them probably know, most of them probably know a lot more than me. And the best advice I got so far is, yeah, use fog. Use what? All right. That's it.
 All right, I think we're there. Hi everyone, my name is Yara Pellusen. I come from the  Norwegian mapping authorities where I worked the last six years. My background  is mainly within post-GIS work, backend stuff, some configuring of  services, stuff like that. So me venturing into the world of 3JS and  JavaScript in general has been a, let's call it a learning experience. So what I'm  going to present today is the state of this projects mine, WXS.3JS, which is  basically trying to visualize, make a 3D map based on services, WCS services,  and initially WMS services, eventually also cached WMTS services. And the end  product will be, is not, will be a sleepy map, the one we know from open layers,  etc. So now that they closed the door, we could probably just start, I guess.  All right, so no good presentation without an overview. We start off with just  like the history background of the project, how it came to be. Then I will  just go into the components that are part of the project right now, give a  brief overview of those. Then since this is a visual project, I'm just going to go  straight into the demo. I will use some time on GitHub, just looking to the code,  showing everywhere, everyone where stuff is, and also hopefully I will be able to  do a couple of live demos, knock on wood. So yeah, I'm going to try to summarize  afterwards by going through a good, bad, ugly, and also try to sketch out the  future, as I see it, and end up with a summary. For those of you who read the  description of this talk, you will have noticed that I'm actually looking for  developers. It would be really cool. But, and also the, I should mention that the  project is a MIT licensed, so you're free to basically do whatever you want with  it, if you find it, find it to your liking. All right, so the history. The idea  came about, I was attending a hackathon in Norway with the like cultural  ministry, which I was there representing the national mapping  authorities, trying to educate people on how to use our data in their products.  And being in such an environment, you tend to get, well, inspired really, because  there's a lot of people around you, they're all hacking, they're all got their  ideas. And I, sitting there, I remembered reading this blog. This guy, Björn  Sönlik, wrote this blog post on how he basically took a digital elevation model  and married it with 3JS to create this. I thought, wow, that's really cool. I want  to do that. Then I took a, I figured, well, since I work with services mainly,  that's my main job, that's what I do, I create services. And for a long time,  the longest time we had this WCS service, which I don't know, is everyone familiar  with WCS? Is that, oh, sorry, is anyone not familiar with WCS? Everyone? Okay.  WCS is a raster-based, it delivers rasters, it's like WMS, except you get the  data instead of just a picture. So I made this WCS service. The problem was no one  was using it. So this would be a really good idea to sort of show off the  service and maybe show how you can use, utilize the WCS service on the fly, et cetera.  So I started out. Let me just go straight into this one as well.  First thing I noticed was there was a disjoint between WCS, or the formats that  WCS wants to give you. Basically, I only had it configured for GeoTiffs. Turns out  browsers don't like Tiff files. They don't want to have anything to do with  that. So that was a problem. So I could order the elevations, I got them, but I  couldn't do anything with them. So, okay, well, figure, let's hack around that.  So I set up the WCS so that I now can give XYZ files. That's fine and dandy.  So now I get the elevations. And now all I had to do was plug in the WMS get URL.  And basically what I ended up with there was, oops, let's see, it's better from this  perspective, 3D model like that, which is created based on nothing but a bounding box,  really. Give it a bounding box. It's going to query the WCS, it queries the WMS, and  it meshes it together and wham bam, 3JS. Brilliant tool, really. So, yeah. For those  of you who haven't used 3JS, I would suggest going to this place just to need to plug there.  It's a wealth of inspiration in there. I will not go into the details of each of them.  Just know that it's there. Okay, presentation, presentation. All right.  So for the components. All right. It's very easy and it's very lightweight. The project  has only been around for like six months. The code base is 1,000 lines. So I'm trying  to keep it simple. But we need, of course, obviously we need 3JS for the visualization.  After long last, I did find this TIFFJS, which enabled me to get around the problem of using  the XYZ files. XYZ files is very, very big. I mean, you get, it's basically text files.  So it's not compressed at all. So it takes a while to get the data. Using TIFFJS, I was  able to read the TIFF files from the WCS. Brilliant little piece of JavaScript in there.  Some limitations to it. I so far, I haven't been able to get an array of length larger  than 2048. But I'm sure that eventually we'll get through that as well.  Services initially, we use WMS and WCS. And again, for those who read the description of  this talk, it says that we're planning to do WMTS. Yay! Actually, we do now. The current  code will use WMTS, it uses tiles. There are some problems with it. And as much as I sort  of broke the WMS implementation, so now you need to have a tile set. But it works as long  as you're in Norway. But it's not a problem. You just, if you plug in another tile set,  it should work out of the box. And it is easy to fix. I've just been sort of busy doing  other stuff. Aren't we all? So demo-wise, first, oh, no, no, no, you weren't supposed  to see that. Okay, so get up page. We are three people who committed to do the project  so far. You can tell that this part over here was the initial, when we initially did it,  you'll find that this is the vacation. And then this is me getting nervous before this  talk. But there's been, like I said, it's not very six months old. There is a total  of a thousand lines of code, about 80 commits in total. So fairly young. The structure is,  again, quite basic. Got your external libraries here, get your source code in here. I'm just  going to go briefly through the organization of this because, oh, yeah, I didn't mention.  None of this is documented. The page where I show you the labs.CardFerke.no page has  some documentation of the parameters that it takes. You can parameterize it using SRS  or like coordinate system projections or you can use your own WCS in the URL, which layers  are you using, what coverage are you using, stuff like that. It's in the article. But  the best place is actually this part. Fairly simple, really. This thing here checks in  the URL you're using to see if any of these keywords are there. Fetch its value and assigns  it to the variable. Then it's reused throughout. What else is I said? I was saying this wasn't  documented. This is documented. All right. So that was the universe part of it. This  one everyone should ignore because it's not there, really. So then you have the WCS and  WMTS loaders, really. What they do is they basically enable you. The WCS here takes a  TIFF file and would basically iterate through a geometry, a TIFF, sorry, a 3JS geometry  and assign the Z values to the corresponding vertices throughout. The meat of the project  is in this file. It is not very big, but it's the thing that sort of tries to sew everything  together. It is where you will find it. It will sort out what the different bounding  boxes are. It will fetch the tiles and, well, it's where everything happens. It's a big  factory. If you ever tried to use this, this is probably where you will start scratching  your head and say, what on earth is going on here? Yes. So now is when I show you the  pretty pictures and pray to the techno gods. Let's start with this one. This is the standard  area that I use for testing purposes. So basically, we have your 3D model right here. In this  case, I preloaded this because I don't, but it should load fairly quickly. Notice also  that this is using a WMS. That was, now let's try the sleepy part. Hopefully this works because  in theory, yeah, here we go. That was a bit scary. So I'm going to try to refresh this  page since it seemed to work. Notice also in the URL, you have a bounding box up here.  You have a layer defined at the end. And now it doesn't load. Yeah. Look at that. Luckily,  I have another demo to show. I figured I'd just show off how you can use, this is just  my example implementation. You can make much more fancy. I'm not a designer. So if you're  a designer, you probably have a, you probably like get your head down in your lap right  now, scratching your eyeballs out or something. But the idea here being that you define a  bounding box over here and, God, this really, I hope this works. And what you're not seeing  right now is the 3D model appearing where it should be. Yeah, yeah, oh, I forgot. I forgot.  I forgot. Of course, it's nighttime. Yeah. Yeah. That was too bad. That was going to  be the big piece de resistance. Look at that. While you're not looking. So the next thing  I was going to show that was supposed to go really fast is you can change your layers  over here and you click the button and it's nighttime again. Yeah, okay. I swear this  works. Anyway, that sucks. Oh, okay. Excellent. Okay. So, yeah, okay. So here you have your  3D. See, this is really fancy when it works but what a downer. I swear it's faster when,  but right now I know this is from a server in Norway and probably the network here isn't.  Yeah, I'm playing the network. Okay. So you're all seeing it work. That's great. I'm not  going to try any more demos. So we jump to the good, bad, and ugly. So the good stuff  is it is, should be, fairly easy to use for when it's set up properly. The fact that you  can just define your parameters in the URL makes it easy to just construct your URL and  then you bang, you get your 3D model up and running. I also listed the potential there.  Seeing as, to my mind, it does have a lot of potential. I know there are people out there  who make much more fancy graphics and they make their globes and everything is looking  really nice. This does one thing and hopefully it should do it really well. I listed a few  bugs. Colbeys of a thousand lines. There's a limit to how many bugs you can get. It does  still have some do pop up now and then but so bad stuff. Well, low maturity, that's a  given. But I find that it's really rewarding to work with it because there's still so many  things to do. So you can actually work on something. You don't nitpick on a small bug  that no one's ever going to notice. You can actually make new features in this. There's  no projections. That's part of the keeping it simple. Right now, you sort of have to  use the same projection on your WCS as your, whatever you're overlaying, WMS, WMTS. And  yes, as I mentioned earlier, the lack of documentation can be an issue. Ugly. Yes, some of the code  is ugly. Particularly the part when I just, I think the latest commit I did tried to average  values in the corners between tiles. That's not easy and I have no idea. I'm not sure  that I even can understand the code myself right now. So hopefully someone will make  it more legible at some point. I got to the point where it worked and then it was hands  off. Clunky navigation. Yes, so far I haven't done anything to the navigation. Just use the  standard one that I found in an example somewhere. And that is a big one that should be fixed.  It is a big piece of work getting that because it ties into a lot of other things. Like if  you want this to be a true slip map, you want to be able to do, you need to be able to change  some levels and stuff like that. And that ties into navigation of the camera. So it's  a big piece of work that needs doing. Yeah. And as I mentioned earlier, right now it's  sort of a hard code to use WMTS. It could be fixed fairly easy but it's going to be ugly  because if you try to use this and you're sort of outside of Norway, it might break entirely.  Yeah. So it brings us to the future of this. I imagine, well, these three things, two of  them, the first two should be doable in my lifetime. Changing zoom levels dynamically.  Right now it doesn't do that at all. You get the zoom level that sort of corresponds to  the initial bounding box you start with and that's what you're stuck with. But there is  some considerations taking to account there with like level of details because, you know,  the classic way of doing this is that you have higher resolution tiles close to where  you're looking from and then you have lower resolution tiles further away. The problem  is that then you then query different zoom levels and if you have different generalization,  it tends to start looking ugly quite quick. It's my experience anyway. Of course, the  other way to do it is to create a, to tailor WMTS and WMS service for the specific use  but then that wouldn't be general enough. I want something more general than that. So  I haven't really tackled that problem yet. All right, optimizing geometry. Yes, big one.  Right now we load tiles, we load geometry and we just sort of stack them together, do  a little bit of edge trying to sort them together along the edges, not much more than that.  I have read documentation on how to merge it. Still haven't really gone into that one,  particularly because I haven't figured out whether or not we're going to reuse the geometry  or just get some new geometry. All right, those are the two ways to go. No idea which  one is the better. Still, I'm fairly optimistic that changing zoom levels and optimizing geometry  should be quite possible to do quite soon, which brings me to the third one, the WFS.  Yeah. I imagine the first one, importing geo-json could be done. I mean, there must be libraries  out there. You can read geo-json from WFS and then sort of mapping those up to 3JS and  its geometry types should be fairly easy. GML, I'm not as certain. Well, I put it up  there because it is an interesting problem that could be tackled. So, yeah, just put  this one together so everyone wants to take a picture. This is the information you need.  And I'm just going to wrap it up there. Thank you.  Does the fact that we really just need 2.5D help the ability to do the navigation, the  slippy part, so we can get rid of the pivoting part? And then that makes it easier to just  navigate kind of up and down and forward and back, side to side.  Yes. Yes. I thought I should probably make that distinction earlier on because someone  was bound to point out that it's not 3D, it's 2.5D. But, yeah, that is basically what I'm  leveraging right now. Do you do any level of detail rendering with the trains or do  you have any plans for really large landscapes?  That's the thing I really haven't figured out how to do yet. I mean, the geometry is  easy. But getting the graphics to tie together, that's the problem. I mean, I've asked several  people about this and some of them probably know, most of them probably know a lot more  than me. And the best advice I got so far is, yeah, use fog.  Use what?  All right. That's it.
05_Jarle_Pedersen_0_1871.png 05_Jarle_Pedersen_1872_4763.png 05_Jarle_Pedersen_4764_5003.png 05_Jarle_Pedersen_5004_9863.png 05_Jarle_Pedersen_9864_13187.png 05_Jarle_Pedersen_13188_17027.png 05_Jarle_Pedersen_17028_18431.png 05_Jarle_Pedersen_18432_18551.png 05_Jarle_Pedersen_18552_19007.png 05_Jarle_Pedersen_19008_19319.png 05_Jarle_Pedersen_19320_19859.png 05_Jarle_Pedersen_19860_20519.png 05_Jarle_Pedersen_20520_24215.png 05_Jarle_Pedersen_24216_24311.png 05_Jarle_Pedersen_24312_29651.png 05_Jarle_Pedersen_29652_34139.png 05_Jarle_Pedersen_34140_34199.png 05_Jarle_Pedersen_34200_34259.png 05_Jarle_Pedersen_34260_34451.png 05_Jarle_Pedersen_34452_34499.png 05_Jarle_Pedersen_34500_34775.png 05_Jarle_Pedersen_34776_35123.png 05_Jarle_Pedersen_35124_35399.png 05_Jarle_Pedersen_35400_35783.png 05_Jarle_Pedersen_35784_36623.png 05_Jarle_Pedersen_36624_36707.png 05_Jarle_Pedersen_36708_36715.png