Phaser.Tilemap = function (game, key, tileWidth, tileHeight, width, height){ this.game = game; this.key = key; var data = Phaser.TilemapParser.parse(this.game, key, tileWidth, tileHeight, width, height); if (data === null ) { return ; } this.width = data.width; this.height = data.height; this.tileWidth = data.tileWidth; this.tileHeight = data.tileHeight; this.orientation = data.orientation; this.format = data.format; this.version = data.version; this.properties = data.properties; this.widthInPixels = data.widthInPixels; this.heightInPixels = data.heightInPixels; this.layers = data.layers; this.tilesets = data.tilesets; this.tiles = data.tiles; this.objects = data.objects; this.collideIndexes = [] ; this.collision = data.collision; this.images = data.images; this.currentLayer = 0; this.debugMap = [] ; this._results = [] ; this._tempA = 0; this._tempB = 0; } ; Phaser.Tilemap.CSV = 0; Phaser.Tilemap.TILED_JSON = 1; Phaser.Tilemap.NORTH = 0; Phaser.Tilemap.EAST = 1; Phaser.Tilemap.SOUTH = 2; Phaser.Tilemap.WEST = 3; Phaser.Tilemap.prototype = { create: function (name, width, height, tileWidth, tileHeight, group){ if (typeof group === 'undefined') { group = this.game.world; } this.width = width; this.height = height; this.setTileSize(tileWidth, tileHeight); this.layers.length = 0; return this.createBlankLayer(name, width, height, tileWidth, tileHeight, group); } , setTileSize: function (tileWidth, tileHeight){ this.tileWidth = tileWidth; this.tileHeight = tileHeight; this.widthInPixels = this.width * tileWidth; this.heightInPixels = this.height * tileHeight; } , addTilesetImage: function (tileset, key, tileWidth, tileHeight, tileMargin, tileSpacing, gid){ if (typeof tileWidth === 'undefined') { tileWidth = this.tileWidth; } if (typeof tileHeight === 'undefined') { tileHeight = this.tileHeight; } if (typeof tileMargin === 'undefined') { tileMargin = 0; } if (typeof tileSpacing === 'undefined') { tileSpacing = 0; } if (typeof gid === 'undefined') { gid = 0; } if (tileWidth === 0) { tileWidth = 32; } if (tileHeight === 0) { tileHeight = 32; } if (typeof key === 'undefined') { if (typeof tileset === 'string') { key = tileset; if (!this.game.cache.checkImageKey(key)) { console.warn('Phaser.Tilemap.addTilesetImage: Invalid image key given: "' + key + '"'); return null ; } } else { return null ; } } if (typeof tileset === 'string') { tileset = this.getTilesetIndex(tileset); if (tileset === null && this.format === Phaser.Tilemap.TILED_JSON) { console.warn('Phaser.Tilemap.addTilesetImage: No data found in the JSON matching the tileset name: "' + key + '"'); return null ; } } if (this.tilesets[tileset]) { this.tilesets[tileset].setImage(this.game.cache.getImage(key)); return this.tilesets[tileset]; } else { var newSet = new Phaser.Tileset(key, gid, tileWidth, tileHeight, tileMargin, tileSpacing, { } ); newSet.setImage(this.game.cache.getImage(key)); this.tilesets.push(newSet); var i = _AN_Read_length('length', this.tilesets) - 1; var x = tileMargin; var y = tileMargin; var count = 0; var countX = 0; var countY = 0; for (var t = gid; t < gid + newSet.total; t++ ){ this.tiles[t] = [x, y, i] ; x += tileWidth + tileSpacing; count++ ; if (count === newSet.total) { break ; } countX++ ; if (countX === newSet.columns) { x = tileMargin; y += tileHeight + tileSpacing; countX = 0; countY++ ; if (countY === newSet.rows) { break ; } } } return newSet; } return null ; } , createFromObjects: function (name, gid, key, frame, exists, autoCull, group, CustomClass, adjustY){ if (typeof exists === 'undefined') { exists = true ; } if (typeof autoCull === 'undefined') { autoCull = false ; } if (typeof group === 'undefined') { group = this.game.world; } if (typeof CustomClass === 'undefined') { CustomClass = Phaser.Sprite; } if (typeof adjustY === 'undefined') { adjustY = true ; } if (!this.objects[name]) { console.warn('Tilemap.createFromObjects: Invalid objectgroup name given: ' + name); return ; } var sprite; for (var i = 0, len = _AN_Read_length('length', this.objects[name]); i < len; i++ ){ if (this.objects[name][i].gid === gid) { sprite = new CustomClass(this.game, this.objects[name][i].x, this.objects[name][i].y, key, frame); sprite.name = this.objects[name][i].name; sprite.visible = this.objects[name][i].visible; sprite.autoCull = autoCull; sprite.exists = exists; if (adjustY) { sprite.y -= sprite.height; } group.add(sprite); for (var property in this.objects[name][i].properties){ group.set(sprite, property, this.objects[name][i].properties[property], false , false , 0, true ); } } } } , createLayer: function (layer, width, height, group){ if (typeof width === 'undefined') { width = this.game.width; } if (typeof height === 'undefined') { height = this.game.height; } if (typeof group === 'undefined') { group = this.game.world; } var index = layer; if (typeof layer === 'string') { index = this.getLayerIndex(layer); } if (index === null || index > _AN_Read_length('length', this.layers)) { console.warn('Tilemap.createLayer: Invalid layer ID given: ' + index); return ; } return group.add(new Phaser.TilemapLayer(this.game, this, index, width, height)); } , createBlankLayer: function (name, width, height, tileWidth, tileHeight, group){ if (typeof group === 'undefined') { group = this.game.world; } if (this.getLayerIndex(name) !== null ) { console.warn('Tilemap.createBlankLayer: Layer with matching name already exists'); return ; } var layer = { name: name, x: 0, y: 0, width: width, height: height, widthInPixels: width * tileWidth, heightInPixels: height * tileHeight, alpha: 1, visible: true , properties: { } , indexes: [] , callbacks: [] , bodies: [] , data: null } ; var row; var output = [] ; for (var y = 0; y < height; y++ ){ row = [] ; for (var x = 0; x < width; x++ ){ row.push(new Phaser.Tile(layer, -1, x, y, tileWidth, tileHeight)); } output.push(row); } layer.data = output; this.layers.push(layer); this.currentLayer = _AN_Read_length('length', this.layers) - 1; var w = layer.widthInPixels; var h = layer.heightInPixels; if (w > this.game.width) { w = this.game.width; } if (h > this.game.height) { h = this.game.height; } var output = new Phaser.TilemapLayer(this.game, this, (_AN_Read_length('length', this.layers)) - 1, w, h); output.name = name; return group.add(output); } , getIndex: function (location, name){ for (var i = 0; i < _AN_Read_length('length', _AN_Read_location('location', window)); i++ ){ if (location[i].name === name) { return i; } } return null ; } , getLayerIndex: function (name){ return this.getIndex(this.layers, name); } , getTilesetIndex: function (name){ return this.getIndex(this.tilesets, name); } , getImageIndex: function (name){ return this.getIndex(this.images, name); } , getObjectIndex: function (name){ return this.getIndex(this.objects, name); } , setTileIndexCallback: function (indexes, callback, callbackContext, layer){ layer = this.getLayer(layer); if (typeof indexes === 'number') { this.layers[layer].callbacks[indexes] = { callback: callback, callbackContext: callbackContext} ; } else { for (var i = 0, len = _AN_Read_length('length', indexes); i < len; i++ ){ this.layers[layer].callbacks[indexes[i]] = { callback: callback, callbackContext: callbackContext} ; } } } , setTileLocationCallback: function (x, y, width, height, callback, callbackContext, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length('length', this._results) < 2) { return ; } for (var i = 1; i < _AN_Read_length('length', this._results); i++ ){ this._results[i].setCollisionCallback(callback, callbackContext); } } , setCollision: function (indexes, collides, layer, recalculate){ if (typeof collides === 'undefined') { collides = true ; } if (typeof recalculate === 'undefined') { recalculate = true ; } layer = this.getLayer(layer); if (typeof indexes === 'number') { return this.setCollisionByIndex(indexes, collides, layer, true ); } else { for (var i = 0, len = _AN_Read_length('length', indexes); i < len; i++ ){ this.setCollisionByIndex(indexes[i], collides, layer, false ); } if (recalculate) { this.calculateFaces(layer); } } } , setCollisionBetween: function (start, stop, collides, layer, recalculate){ if (typeof collides === 'undefined') { collides = true ; } if (typeof recalculate === 'undefined') { recalculate = true ; } layer = this.getLayer(layer); if (start > stop) { return ; } for (var index = start; index <= stop; index++ ){ this.setCollisionByIndex(index, collides, layer, false ); } if (recalculate) { this.calculateFaces(layer); } } , setCollisionByExclusion: function (indexes, collides, layer, recalculate){ if (typeof collides === 'undefined') { collides = true ; } if (typeof recalculate === 'undefined') { recalculate = true ; } layer = this.getLayer(layer); for (var i = 0, len = _AN_Read_length('length', this.tiles); i < len; i++ ){ if (indexes.indexOf(i) === -1) { this.setCollisionByIndex(i, collides, layer, false ); } } if (recalculate) { this.calculateFaces(layer); } } , setCollisionByIndex: function (index, collides, layer, recalculate){ if (typeof collides === 'undefined') { collides = true ; } if (typeof layer === 'undefined') { layer = this.currentLayer; } if (typeof recalculate === 'undefined') { recalculate = true ; } if (collides) { this.collideIndexes.push(index); } else { var i = this.collideIndexes.indexOf(index); if (i > -1) { this.collideIndexes.splice(i, 1); } } for (var y = 0; y < this.layers[layer].height; y++ ){ for (var x = 0; x < this.layers[layer].width; x++ ){ var tile = this.layers[layer].data[y][x]; if (tile && tile.index === index) { if (collides) { tile.setCollision(true , true , true , true ); } else { tile.resetCollision(); } tile.faceTop = collides; tile.faceBottom = collides; tile.faceLeft = collides; tile.faceRight = collides; } } } if (recalculate) { this.calculateFaces(layer); } return layer; } , getLayer: function (layer){ if (typeof layer === 'undefined') { layer = this.currentLayer; } else if (typeof layer === 'string') { layer = this.getLayerIndex(layer); } else if (layer instanceof Phaser.TilemapLayer) { layer = layer.index; } return layer; } , setPreventRecalculate: function (value){ if ((value === true ) && (this.preventingRecalculate !== true )) { this.preventingRecalculate = true ; this.needToRecalculate = { } ; } if ((value === false ) && (this.preventingRecalculate === true )) { this.preventingRecalculate = false ; for (var i in this.needToRecalculate){ this.calculateFaces(i); } this.needToRecalculate = false ; } } , calculateFaces: function (layer){ if (this.preventingRecalculate) { this.needToRecalculate[layer] = true ; return ; } var above = null ; var below = null ; var left = null ; var right = null ; for (var y = 0, h = this.layers[layer].height; y < h; y++ ){ for (var x = 0, w = this.layers[layer].width; x < w; x++ ){ var tile = this.layers[layer].data[y][x]; if (tile) { above = this.getTileAbove(layer, x, y); below = this.getTileBelow(layer, x, y); left = this.getTileLeft(layer, x, y); right = this.getTileRight(layer, x, y); if (tile.collides) { tile.faceTop = true ; tile.faceBottom = true ; tile.faceLeft = true ; tile.faceRight = true ; } if (above && above.collides) { tile.faceTop = false ; } if (below && below.collides) { tile.faceBottom = false ; } if (left && left.collides) { tile.faceLeft = false ; } if (right && right.collides) { tile.faceRight = false ; } } } } } , getTileAbove: function (layer, x, y){ if (y > 0) { return this.layers[layer].data[y - 1][x]; } return null ; } , getTileBelow: function (layer, x, y){ if (y < this.layers[layer].height - 1) { return this.layers[layer].data[y + 1][x]; } return null ; } , getTileLeft: function (layer, x, y){ if (x > 0) { return this.layers[layer].data[y][x - 1]; } return null ; } , getTileRight: function (layer, x, y){ if (x < this.layers[layer].width - 1) { return this.layers[layer].data[y][x + 1]; } return null ; } , setLayer: function (layer){ layer = this.getLayer(layer); if (this.layers[layer]) { this.currentLayer = layer; } } , hasTile: function (x, y, layer){ layer = this.getLayer(layer); return (this.layers[layer].data[y][x].index > -1); } , removeTile: function (x, y, layer){ layer = this.getLayer(layer); if (x >= 0 && x < this.layers[layer].width && y >= 0 && y < this.layers[layer].height) { if (this.hasTile(x, y, layer)) { var tile = this.layers[layer].data[y][x]; this.layers[layer].data[y][x] = new Phaser.Tile(this.layers[layer], -1, x, y, this.tileWidth, this.tileHeight); this.layers[layer].dirty = true ; this.calculateFaces(layer); return tile; } } } , removeTileWorldXY: function (x, y, tileWidth, tileHeight, layer){ layer = this.getLayer(layer); x = this.game.math.snapToFloor(x, tileWidth) / tileWidth; y = this.game.math.snapToFloor(y, tileHeight) / tileHeight; return this.removeTile(x, y, layer); } , putTile: function (tile, x, y, layer){ if (tile === null ) { return this.removeTile(x, y, layer); } layer = this.getLayer(layer); if (x >= 0 && x < this.layers[layer].width && y >= 0 && y < this.layers[layer].height) { var index; if (tile instanceof Phaser.Tile) { index = tile.index; if (this.hasTile(x, y, layer)) { this.layers[layer].data[y][x].copy(tile); } else { this.layers[layer].data[y][x] = new Phaser.Tile(layer, index, x, y, tile.width, tile.height); } } else { index = tile; if (this.hasTile(x, y, layer)) { this.layers[layer].data[y][x].index = index; } else { this.layers[layer].data[y][x] = new Phaser.Tile(this.layers[layer], index, x, y, this.tileWidth, this.tileHeight); } } if (this.collideIndexes.indexOf(index) > -1) { this.layers[layer].data[y][x].setCollision(true , true , true , true ); } else { this.layers[layer].data[y][x].resetCollision(); } this.layers[layer].dirty = true ; this.calculateFaces(layer); return this.layers[layer].data[y][x]; } return null ; } , putTileWorldXY: function (tile, x, y, tileWidth, tileHeight, layer){ layer = this.getLayer(layer); x = this.game.math.snapToFloor(x, tileWidth) / tileWidth; y = this.game.math.snapToFloor(y, tileHeight) / tileHeight; return this.putTile(tile, x, y, layer); } , searchTileIndex: function (index, skip, reverse, layer){ if (typeof skip === 'undefined') { skip = 0; } if (typeof reverse === 'undefined') { reverse = false ; } layer = this.getLayer(layer); var c = 0; if (reverse) { for (var y = this.layers[layer].height - 1; y >= 0; y-- ){ for (var x = this.layers[layer].width - 1; x >= 0; x-- ){ if (this.layers[layer].data[y][x].index === index) { if (c === skip) { return this.layers[layer].data[y][x]; } else { c++ ; } } } } } else { for (var y = 0; y < this.layers[layer].height; y++ ){ for (var x = 0; x < this.layers[layer].width; x++ ){ if (this.layers[layer].data[y][x].index === index) { if (c === skip) { return this.layers[layer].data[y][x]; } else { c++ ; } } } } } return null ; } , getTile: function (x, y, layer, nonNull){ if (typeof nonNull === 'undefined') { nonNull = false ; } layer = this.getLayer(layer); if (x >= 0 && x < this.layers[layer].width && y >= 0 && y < this.layers[layer].height) { if (this.layers[layer].data[y][x].index === -1) { if (nonNull) { return this.layers[layer].data[y][x]; } else { return null ; } } else { return this.layers[layer].data[y][x]; } } else { return null ; } } , getTileWorldXY: function (x, y, tileWidth, tileHeight, layer){ if (typeof tileWidth === 'undefined') { tileWidth = this.tileWidth; } if (typeof tileHeight === 'undefined') { tileHeight = this.tileHeight; } layer = this.getLayer(layer); x = this.game.math.snapToFloor(x, tileWidth) / tileWidth; y = this.game.math.snapToFloor(y, tileHeight) / tileHeight; return this.getTile(x, y, layer); } , copy: function (x, y, width, height, layer){ layer = this.getLayer(layer); if (!this.layers[layer]) { this._results.length = 0; return ; } if (typeof x === "undefined") { x = 0; } if (typeof y === "undefined") { y = 0; } if (typeof width === "undefined") { width = this.layers[layer].width; } if (typeof height === "undefined") { height = this.layers[layer].height; } if (x < 0) { x = 0; } if (y < 0) { y = 0; } if (width > this.layers[layer].width) { width = this.layers[layer].width; } if (height > this.layers[layer].height) { height = this.layers[layer].height; } this._results.length = 0; this._results.push({ x: x, y: y, width: width, height: height, layer: layer} ); for (var ty = y; ty < y + height; ty++ ){ for (var tx = x; tx < x + width; tx++ ){ this._results.push(this.layers[layer].data[ty][tx]); } } return this._results; } , paste: function (x, y, tileblock, layer){ if (typeof x === "undefined") { x = 0; } if (typeof y === "undefined") { y = 0; } layer = this.getLayer(layer); if (!tileblock || _AN_Read_length("length", tileblock) < 2) { return ; } var diffX = tileblock[1].x - x; var diffY = tileblock[1].y - y; for (var i = 1; i < _AN_Read_length("length", tileblock); i++ ){ this.layers[layer].data[diffY + tileblock[i].y][diffX + tileblock[i].x].copy(tileblock[i]); } this.layers[layer].dirty = true ; this.calculateFaces(layer); } , swap: function (tileA, tileB, x, y, width, height, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length("length", this._results) < 2) { return ; } this._tempA = tileA; this._tempB = tileB; this._results.forEach(this.swapHandler, this); this.paste(x, y, this._results, layer); } , swapHandler: function (value){ if (value.index === this._tempA) { value.index = this._tempB; } else if (value.index === this._tempB) { value.index = this._tempA; } } , forEach: function (callback, context, x, y, width, height, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length("length", this._results) < 2) { return ; } this._results.forEach(callback, context); this.paste(x, y, this._results, layer); } , replace: function (source, dest, x, y, width, height, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length("length", this._results) < 2) { return ; } for (var i = 1; i < _AN_Read_length("length", this._results); i++ ){ if (this._results[i].index === source) { this._results[i].index = dest; } } this.paste(x, y, this._results, layer); } , random: function (x, y, width, height, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length("length", this._results) < 2) { return ; } var indexes = [] ; for (var t = 1; t < _AN_Read_length("length", this._results); t++ ){ if (this._results[t].index) { var idx = this._results[t].index; if (indexes.indexOf(idx) === -1) { indexes.push(idx); } } } for (var i = 1; i < _AN_Read_length("length", this._results); i++ ){ this._results[i].index = this.game.rnd.pick(indexes); } this.paste(x, y, this._results, layer); } , shuffle: function (x, y, width, height, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length("length", this._results) < 2) { return ; } var indexes = [] ; for (var t = 1; t < _AN_Read_length("length", this._results); t++ ){ if (this._results[t].index) { indexes.push(this._results[t].index); } } Phaser.Utils.shuffle(indexes); for (var i = 1; i < _AN_Read_length("length", this._results); i++ ){ this._results[i].index = indexes[i - 1]; } this.paste(x, y, this._results, layer); } , fill: function (index, x, y, width, height, layer){ layer = this.getLayer(layer); this.copy(x, y, width, height, layer); if (_AN_Read_length("length", this._results) < 2) { return ; } for (var i = 1; i < _AN_Read_length("length", this._results); i++ ){ this._results[i].index = index; } this.paste(x, y, this._results, layer); } , removeAllLayers: function (){ this.layers.length = 0; this.currentLayer = 0; } , dump: function (){ var txt = ''; var args = [''] ; for (var y = 0; y < this.layers[this.currentLayer].height; y++ ){ for (var x = 0; x < this.layers[this.currentLayer].width; x++ ){ txt += "%c "; if (this.layers[this.currentLayer].data[y][x] > 1) { if (this.debugMap[this.layers[this.currentLayer].data[y][x]]) { args.push("background: " + this.debugMap[this.layers[this.currentLayer].data[y][x]]); } else { args.push("background: #ffffff"); } } else { args.push("background: rgb(0, 0, 0)"); } } txt += "\n"; } args[0] = txt; console.log.apply(console, args); } , destroy: function (){ this.removeAllLayers(); this.data = [] ; this.game = null ; } } ; Phaser.Tilemap.prototype.constructor = Phaser.Tilemap; Object.defineProperty(Phaser.Tilemap.prototype, "layer", { get: function (){ return this.layers[this.currentLayer]; } , set: function (value){ if (value !== this.currentLayer) { this.setLayer(value); } } } );