Tutorial: The Simplest Map

The links below will take you to code samples for two maps containing simple vector data.

  • Simple Map to Get Data From a URL - uses a URL to get the data and requires a web server
  • Simple Map to Set Data from a Local File (Map_Simplest_SetData.html) - only uses local data, does not require a web server (you'll need to run this map by double-clicking on it in the file explorer).

If you are using a web server, use the first code sample, otherwise, use the second one. Click on the link and you should see the default CanvasMap display on the web page.

Note that the footer for the map will include an error message as we have simplified the code and removed the projector that would normally provide geographic coordinates in the footer. You can ignore this for now as we'll add the projector back in a future tutorial.

Do a view source on the code and you'll see several sections of code divided by lines of asterisks ("*"). These sections are:

  • Start of the HTML file
  • Functions to control CanvasMap: Functions to start up and control the map
  • Includes: JavaScript and CSS files
  • Start of HTML Body: The remainder of the HTML including the one tag for the map, "MapContainer_0"

There are a number of JavaScript files included and you only need to include those that are needed for your specific map. CanvasMap also uses jQuery so you'll need to load a version of it. We include one that is compatible with the current version of CanvasMap.

The only function we need for the default map below is an "initialization" or "init()" function to setup the map with the desired layers. We also need to have a global variable to hold on to the CanvasMap object. This is the main object that we will interact with in future tutorials to customize the map.

The body of the HTML just has the one tag we need for the "MapContainer_0" element. This is the element that the map will be placed into when "Initialize()" is called.

Initializing the map

Take a look at the "init()" function and you'll see code to initialize the map, add layers, and start the map.

The code below will:

  • Create the CanvasMap object and save it to the global variable
  • Set the location of the images folder. This tells CanvasMap where to find the images. The current setting should work as long as you have your maps stored in the "CanvasMap" folder. If you move them, you'll need to update the image folder.
  • Initialize the CanvasMap. The "Initialization()" function sets up the internal state of the CanvasMap so we can add layers to it.
TheCanvasMap=new CanvasMap(); // creates the map object
	
TheCanvasMap.SetImageFolder("Images/"); // lets CanvasMap know where the images are
	
TheCanvasMap.Initialize(); // sets up the view, scene, and event handlers for the map

The code below adds a layer to the map. "CMLayerGeoJSON" displays polygon and linestring (i.e. polyline) data in the map. There are other layer types we'll learn about in future tutorials. This code takes the following steps:

  • Create the layer
  • Give the layer a name which will appear in the layer list
  • Set the URL for where the data is located. Note that we also send the layer the "CMView" that is within the CanvasMap (more on this later) and a flag "true" indicating we want CanvasMap to "ZoomTo" this layer after it is loaded. Note that if you are running without a server and used the "Set Data" page, you'll have a "SetData()" function instead of the "SetURL()" function.
  • Set the style of the layer to be filled with "PaleGreen"
  • Add the layer to the CanvasMap
var Layer_HumboldtCountry=new CMLayerGeoJSON();

Layer_HumboldtCountry.SetName("Humboldt County");

Layer_HumboldtCountry.SetURL("/GISData/GeoJSON/GoogleMercator/ne_110m_admin_0_countries.js",TheCanvasMap.GetView(),true);

Layer_HumboldtCountry.SetStyle({fillStyle:"PaleGreen"}); // fill the data with pale green color

TheCanvasMap.AddLayer(Layer_HumboldtCountry);

The final step is just to call "StartMap". We have specified a flag of "false" to keep CanvasMap from resizing the map to fit the browser window as the default is to create a resizable map (more on this later).

TheCanvasMap.StartMap(false); // don't resize

Changing Layer Styles

The "SetStyle()" function in a layer lets you change how the layer is displayed. This uses the HTML 5 Canvas styles and is very flexible. This is a good time to try out some different styles and see how they work. Some examples are below and the full list is available at the W3Schools web site.

Some examples include:

Making the countries black with white borders:

 Layer_HumboldtCountry.SetStyle(
{
	fillStyle:"#000000",
	strokeStyle:"#ffffff",
}); 

Thick red lines:

Layer_HumboldtCountry.SetStyle(
{
	fillStyle:"#000000",
	strokeStyle:"#ff0000",
	lineWidth:2,
}); 

Take some time now and play with the different colors and other options for canvas drawing.

Note: The amount of time it takes to paint data into the canvas is dependent upon the amount of data and how complex you make the drawing. If you have very detailed outlines for all the countries in the world, and you add a shadow, don't expect the map to redraw anytime soon!

Changing the Data

The CMLayerGeoJSON class supports GeoJSON data and this tutorial is showing the data in GoogleMercator. Note that I am referring to this as "GoogleMercator". To be compatible with tile layers from OpenStreetMap and other vectors, we need to be using the exact spatial reference that was created with GoogleMaps. This is not a great projection for maps but there are many tile sets out there and we'll be using them in future tutorials (some of them are really cool). For this reason, you'll need to project your data into the GoogleMaps projection. BlueSpray supports this will a custom projection engine and I don't know of another GIS application that does.

To setup data for use in this tutorial, use the following steps:

  • Obtain a shapefile (or other supported format) with polygons or linestrings (polylines) in the spatial reference WGS84, Geographic.
  • Load the file into BlueSpray
  • Right-click on the "Scene" and select "Transforms -> Change SRS".
  • Click on "Explore"
  • Select "GoogleMaps" from the "Projector" menu
  • Uncheck all the options under "Clipping "Settings"
  • Click "Update".
  • Click "OK"
  • Click "OK" and your data should be projected to the GoogleMaps projection.
  • Right click on the layer and select "Export to File..."
  • Save the file with a ".js" extension. This will save it as a GeoJSON formatted file.
  • Move the file to where your web page can access it.

Note that if you are using CanvasMap without a web server, you'll need to add a line to the top of the GeoJSON file such as "var FileName=" so you can load it without using a URL.

Finally, change the string the "SetURL()" or "SetData()" functino to your new file. The data should appear in your map when you refresh the browser.

Raster Layers

You can also add raster layers. The code below will add a single raster from our server. Note the web only supports "PNG" and "JPG" formats and these formats do not provide georeferencing information. You'll need to speify the bounds of the raster as shown be low. The values can be found in BlueSpray by going to "Properties -> Extent" for a raster layer.

//*****************************************************
	
var Layer_World=new CMLayerRaster();
	
Layer_World.SetURL("GISData/Rasters/GoogleMercator/world.topo.bathy.200412.png",TheCanvasMap.GetView()); 
Layer_World.SetName("Blue Marble");
		
var TheBounds = 
{
	XMin: -6214,
	XMax: 6.6978368E7,
	YMin: -8.6442292E7,
	YMax: 1.9333428E7,
}
Layer_World.SetBounds(TheBounds);

TheCanvasMap.AddLayer(Layer_World);

Large Rasters with Pyramids

The method above works for small rasters in small areas. Large rasters need to be turned into "pyramids" of "tiles" to keep the performance fast. This can be done in BlueSpray by right clicking on a raster layer and selecting "Transforms (other) -> To Pyramid Layer ". This will create a pyramid of tiles in BlueSpray. Then, right-click and select "Export to File". Navigate to a folder for the pyramid files and elect "Canvas Map Folder" as the file type. Don't worry about the file name as BlueSpray will put a large number of files in the folder including "pngs" that represent the files, an "info.js" file with information on the raster, and a series of "tile" files with information on each tile.

var Layer_World=new CMLayerPyramid();

TheCanvasMap.AddBackground(Layer_World);

Layer_World.SetURL("/GISData/GoogleMercator/Pyramid/BlueMarble",TheView); 
Layer_World.SetName("BlueMarble");

Note that you do not need to provide the bounds as this is already defined by the tiling standard. You do need to call "AddBackground()" to add a tiled layer as a background but call "AddLayer()" if you want it to appear in the layer list.

Also note that the layer should be convered into the desired spatial reference before converting it to a pyramid.

Large Vector data sets with Pyramids

Vector layers can also slow down a web solution if they are too complicated. Vector layers of small areas, such as islands, can be displayed with GeoJSON but large layers such as a countries of the world layer, need to be converted into a Pyramid of tiles. This can be done for vector layers in exactly the same way as rasters except the "To Pyramid Layer" is in the "Transforms" menu.

var Layer_World=new CMLayerPyramid();

TheCanvasMap.AddBackground(Layer_World);

Layer_World.SetURL("/GISData/GoogleMercator/Pyramid/NaturalEarth_Countries",TheView); 
Layer_World.SetName("Countries");

 

Open Pyramids

Below is an example of adding a pyramid of raster tiles to CanvasMap.

//*****************************************************
// add the LandSat (California) pyramid layer
	
var Layer_California=new CMLayerPyramid();
Layer_California.SetName("California");
		
TheCanvasMap.AddLayer(Layer_California);
		
var TheBounds = 
{
  		XMin: 284384,
 		XMax: 1412832,
 		YMin: 3541824,
 		YMax: 4729664
}
Layer_California.SetBounds(TheBounds);
	
Layer_California.SetURL("/GISData/Pyramids/WGS_84_UTM_10_North/CA_and_Bathy_2_Tiles/Tiles_",TheCanvasMap.GetView());
 

Debugging JavaScript

If you have not already discovered them, the new browsers contain very powerful source-code debuggers that make debugging JavaScript much, much easier than in the past. I highly recommend using one.