Subscribe to GameFromScratch on YouTube Support GameFromScratch on Patreon


22. October 2014

 

 

In this tutorial we are going to look at loading and using Tiled TMX maps.  Tiled is a free, open sourced map editor, and TMX is the file format it outputs.  You basically use it to “paint” levels using one or more spritesheets containing tiles, which you then load and use in your game.

 

Here is Tiled in action, creating the simple map I am going to use in this example:

image

 

By the way, I downloaded the tile graphics from here.  Additionally, you can download the generated TMX file we will be using here.

 

I am not going to go into detail on using the Tiled editor.  I actually covered this earlier here.  For Phaser however, just be certain you export as either JSON or CSV format and you should be good to go.

 

Now let’s look at some code to load the tile map.

 

 

/// <reference path="phaser.d.ts"/>
class SimpleGame {
    game: Phaser.Game;
    map: Phaser.Tilemap;
    
    constructor() {
        this.game = new Phaser.Game(640, 480, Phaser.AUTO, 'content', {
            create: this.create, preload:
            this.preload, render: this.render
        });
    }
    preload() {
        this.game.load.tilemap("ItsTheMap", "map.json", null, Phaser.Tilemap.TILED_JSON);
        this.game.load.image("Tiles", "castle_0.png");
    }
    render() {

    }
    create() {
        this.map = this.game.add.tilemap("ItsTheMap", 32, 32, 50, 20);
        this.map.addTilesetImage("castle_0", "Tiles");

        this.map.createLayer("Background").resizeWorld();
        this.map.createLayer("Midground");
        this.map.createLayer("Foreground");
        
        
        this.game.camera.x = this.map.layers[0].widthInPixels / 2;
        this.game.camera.y = 0;

        this.game.add.tween(this.game.camera).to({ x: 0 }, 3000).
to({ x: this.map.layers[0].widthInPixels }, 3000).loop().start(); } } window.onload = () => { var game = new SimpleGame(); };

 

And when you run it… assuming like me you are using Visual Studio 2013 you will probably see:

image

 

Hmmmm, that’s not good.  Is there something wrong with our tilemap?  Did we make a mistake?

 

Nope… welcome to the wonderful world of XHR requests.  This is a common problem you are going to encounter over and over again when dealing with loading assets from a web server.  If we jump into the debugger, we quickly get the root of the problem:

 

image

 

Let’s look closely at the return value in xhr.responseText:

Ohhh. it’s an IIS error message and the key line is:

The appropriate MIME map is not enabled for the Web site or application.

Ah…

 

See, Visual Studio ships with an embedded version of IIS called IIS Express, and frankly, IIS Express doesn’t have a clue what a JSON file is.  Let’s solve that now.  If you created a new TypeScript project in Visual Studio, it should have created a web.config file for you.  If it didn’t create one and enter the following contents:

<?xml version="1.0" encoding="utf-8"?>
<!--
  For more information on how to configure your ASP.NET application, please visit
  http://go.microsoft.com/fwlink/?LinkId=169433
  -->
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5" />
    <httpRuntime targetFramework="4.5" />
  </system.web>
  <system.webServer>
    <staticContent>
      <mimeMap fileExtension=".json" mimeType="application/json" />
    </staticContent>
  </system.webServer>
</configuration>

 

Now the code should run without error

I should take a moment to point out that this is an entirely Visual Studio specific solution.  However, this particular problem is by no means limited to IIS Express.  I documented a very similar problem when dealing with WebStorm’s integrated Chrome plugin.  If your loadJson call fails, this is most likely the reason why!  Well that or you typo’ed it. :)

 

Ok, assuming everything is configured right,now we should see:

 

 

By the way, you may have to click on the to get it to start rendering.

 

Most of the loading code should look pretty familiar by now, Phaser is remarkably consistent in its approach.  There are a few things to be aware of though from that code.  First, the order you create layers in is important.  In Tiled I created 3 layers of tiles.  A solid background layer named “background”, a middle layer with most of the tiles in it called “midground” then a detail layer for the topmost tiles named “foreground”.  Think of rendering tiles like putting stickers on a flat surface… the front most stickers will obscure the ones that are behind them.  The same is true for tiles.  There are other options in tiled for creating foreground and background layers, but I stuck with normal tile layers for ease.  Just no that more efficient options exist.

 

The next thing to be aware of is when I called addTilesetImage, that is the same image filename that I provided to Tiled.  It is important that you use the same graphics files and names between Tiled and your code.  The next thing worth noticing is the call to resizeWorld() I made when loading the first tiled layer.  This simply set’s the world’s dimensions to be the same size as the tile layer you specified.  Since all the tile layers are the same size, you could have called it on any of them.  Finally, we made a simple tween that pans the camera from one end of the level to the other and back.

 

There is more to touch on with tiles, but I will have to cover that in later post(s).

 

Programming , , , ,

blog comments powered by Disqus

Month List

Popular Comments