-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhex-grid.min.js.map
1 lines (1 loc) · 127 KB
/
hex-grid.min.js.map
1
{"version":3,"sources":["vg.js","Board.js","grids/Cell.js","grids/HexGrid.js","grids/SqrGrid.js","grids/Tile.js","lib/LinkedList.js","lib/Signal.js","pathing/AStarFinder.js","pathing/PathUtil.js","utils/Loader.js","utils/MouseCaster.js","utils/Scene.js","utils/SelectionManager.js","utils/Tools.js"],"names":["vg","VERSION","PI","Math","TAU","DEG_TO_RAD","RAD_TO_DEG","SQRT3","sqrt","TILE","ENT","STR","HEX","SQR","ABS","Board","grid","finderConfig","Error","this","tiles","tileGroup","group","THREE","Object3D","overlay","finder","AStarFinder","Loader","init","setGrid","prototype","setEntityOnTile","entity","tile","pos","cellToPixel","cell","position","copy","y","heightOffset","addTile","i","indexOf","push","snapTileToGrid","add","mesh","removeTile","remove","splice","dispose","removeAllTiles","children","length","getTileAtCell","h","cellToHash","cells","snapToGrid","pixelToCell","getRandomTile","Tools","randomInt","findPath","startTile","endTile","heuristic","newGrid","forEach","t","generateOverlay","size","mat","LineBasicMaterial","color","opacity","generateTilemap","config","reset","generateTiles","constructor","Cell","q","r","s","userData","walkable","_calcCost","_priority","_visited","_parent","uniqueID","LinkedList","generateID","set","equals","HexGrid","type","cellSize","numCells","extrudeSettings","autogenerated","verts","_createVertex","cellShape","Shape","moveTo","x","lineTo","autoClose","cellGeo","Geometry","vertices","verticesNeedUpdate","cellShapeGeo","ShapeGeometry","_cellWidth","_cellLength","_hashDelimeter","_directions","_diagonals","_list","_vec3","Vector3","_cel","_conversionVec","_geoCache","_matCache","TWO_THIRDS","z","_cubeRound","getCellAt","getNeighbors","diagonal","filter","n","l","getRandomCell","c","distance","cellA","cellB","d","max","abs","clearPath","traverse","cb","generateTile","scale","material","height","geo","amount","ExtrudeGeometry","Tile","geometry","settings","tileScale","bevelEnabled","bevelSegments","steps","bevelSize","bevelThickness","merge","generateTilePoly","MeshBasicMaterial","Mesh","rotateOnAxis","generate","overlayObj","overlayMat","createPointsGeometry","line","Line","rotation","load","url","scope","self","getJSON","callback","json","fromJSON","call","cache","toJSON","k","angle","cos","sin","rx","round","ry","rz","xDiff","yDiff","zDiff","SqrGrid","_fullCellSize","half","ceil","MeshPhongMaterial","randomizeRGB","objectType","selected","highlight","structure","emissive","_emissive","getHex","select","setHex","deselect","toggle","parent","LinkedListNode","obj","next","prev","free","first","last","objToNodeMap","Date","now","floor","random","sortArray","toString","slice","getNode","addNode","node","err","console","error","swapObjects","newObj","showDebug","dump","has","moveUp","b","a","oldCNext","moveDown","sort","compare","clear","shift","pop","concat","list","msg","log","SignalBinding","signal","listener","isOnce","listenerContext","priority","_listener","context","active","params","execute","paramsArr","handlerReturn","apply","detach","isBound","_destroy","Signal","_bindings","_prevParams","dispatch","arguments","memorize","_shouldPropagate","validateListener","fnName","replace","_registerListener","binding","prevIndex","_indexOfListener","_addBinding","cur","addOnce","removeAll","getNumListeners","halt","bindings","Array","forget","allowDiagonal","heuristicFilter","startNode","endNode","current","costSoFar","neighbors","PathUtil","backtrace","nodeA","nodeB","path","reverse","biBacktrace","pathA","pathB","pathLength","dx","dy","sum","interpolate","x0","y0","x1","y1","sx","sy","e2","expandPath","coord0","coord1","interpolated","interpolatedLen","j","expanded","len","smoothenPath","ex","ey","newPath","lastValidCoord","coord","testCoord","blocked","isWalkableAt","compressPath","lx","ly","ldx","ldy","sq","compressed","px","py","manager","imageLoader","crossOrigin","LoadingManager","warn","ImageLoader","loadTexture","mapping","onLoad","onError","texture","Texture","image","needsUpdate","evt","sourceFile","MouseCaster","camera","element","down","rightDown","pickedObject","selectedObject","allHits","ctrl","wheel","screenPosition","Vector2","_camera","_raycaster","Raycaster","_preventDefault","document","addEventListener","_onDocumentMouseMove","bind","_onDocumentMouseDown","_onDocumentMouseUp","_onMouseWheel","OVER","OUT","DOWN","UP","CLICK","WHEEL","update","setFromCamera","hit","intersects","intersectObject","object","point","preventDefault","window","event","shiftKey","ctrlKey","which","clientX","innerWidth","clientY","innerHeight","stopPropagation","delta","undefined","wheelDelta","detail","Scene","sceneConfig","controlConfig","sceneSettings","body","alpha","antialias","clearColor","sortObjects","fog","light","DirectionalLight","lightPosition","cameraType","cameraPosition","orthoZoom","controlSettings","minDistance","maxDistance","zoomSpeed","noZoom","renderer","WebGLRenderer","setClearColor","width","container","AmbientLight","normalize","OrthographicCamera","PerspectiveCamera","contolled","controls","OrbitControls","domElement","left","right","top","bottom","aspect","updateProjectionMatrix","setSize","attachTo","style","setPixelRatio","devicePixelRatio","appendChild","render","updateOrthoZoom","focusOn","lookAt","SelectionManager","mouse","onSelect","onDeselect","toggleSelection","onMouse","fireSignal","clearSelection","clamp","val","min","sign","v","getShortRotation","isPlainObject","nodeType","Object","hasOwnProperty","target","src","array","isArray","dst","e","keys","key","nwf","system","Performance","elapsedTime","performance","empty","lastChild","removeChild","radixSort","arr","idxBegin","idxEnd","bit","idx","idxOnes","mask","tmp","base","range","rgb","split","parseInt","substring","xhr","XMLHttpRequest","uri","onreadystatechange","status","JSON","parse","responseText","statusText","open","setRequestHeader","send"],"mappings":"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","file":"hex-grid.min.js","sourcesContent":["var vg = { // eslint-disable-line\n\tVERSION: '0.1.1',\n\n\tPI: Math.PI,\n\tTAU: Math.PI * 2,\n\tDEG_TO_RAD: 0.0174532925,\n\tRAD_TO_DEG: 57.2957795,\n\tSQRT3: Math.sqrt(3), // used often in hex conversions\n\n\t// useful enums for type checking. change to whatever fits your game. these are just examples\n\tTILE: 'tile', // visual representation of a grid cell\n\tENT: 'entity', // dynamic things\n\tSTR: 'structure', // static things\n\n\tHEX: 'hex',\n\tSQR: 'square',\n\tABS: 'abstract'\n};","/*\n\tInterface to the grid. Holds data about the visual representation of the cells (tiles).\n\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n */\nvg.Board = function(grid, finderConfig) {\n\tif (!grid) throw new Error('You must pass in a grid system for the board to use.');\n\n\tthis.tiles = [];\n\tthis.tileGroup = null; // only for tiles\n\n\tthis.group = new THREE.Object3D(); // can hold all entities, also holds tileGroup, never trashed\n\n\tthis.grid = null;\n\tthis.overlay = null;\n\tthis.finder = new vg.AStarFinder(finderConfig);\n\t// need to keep a resource cache around, so this Loader does that, use it instead of THREE.ImageUtils\n\tvg.Loader.init();\n\n\tthis.setGrid(grid);\n};\n\nvg.Board.prototype = {\n\tsetEntityOnTile: function(entity, tile) {\n\t\t// snap an entity's position to a tile; merely copies position\n\t\tvar pos = this.grid.cellToPixel(tile.cell);\n\t\tentity.position.copy(pos);\n\t\t// adjust for any offset after the entity was set directly onto the tile\n\t\tentity.position.y += entity.heightOffset || 0;\n\t\t// remove entity from old tile\n\t\tif (entity.tile) {\n\t\t\tentity.tile.entity = null;\n\t\t}\n\t\t// set new situation\n\t\tentity.tile = tile;\n\t\ttile.entity = entity;\n\t},\n\n\taddTile: function(tile) {\n\t\tvar i = this.tiles.indexOf(tile);\n\t\tif (i === -1) this.tiles.push(tile);\n\t\telse return;\n\n\t\tthis.snapTileToGrid(tile);\n\t\ttile.position.y = 0;\n\n\t\tthis.tileGroup.add(tile.mesh);\n\t\tthis.grid.add(tile.cell);\n\n\t\ttile.cell.tile = tile;\n\t},\n\n\tremoveTile: function(tile) {\n\t\tif (!tile) return; // was already removed somewhere\n\t\tvar i = this.tiles.indexOf(tile);\n\t\tthis.grid.remove(tile.cell);\n\n\t\tif (i !== -1) this.tiles.splice(i, 1);\n\t\t// this.tileGroup.remove(tile.mesh);\n\n\t\ttile.dispose();\n\t},\n\n\tremoveAllTiles: function() {\n\t\tif (!this.tileGroup) return;\n\t\tvar tiles = this.tileGroup.children;\n\t\tfor (var i = 0; i < tiles.length; i++) {\n\t\t\tthis.tileGroup.remove(tiles[i]);\n\t\t}\n\t},\n\n\tgetTileAtCell: function(cell) {\n\t\tvar h = this.grid.cellToHash(cell);\n\t\treturn cell.tile || (typeof this.grid.cells[h] !== 'undefined' ? this.grid.cells[h].tile : null);\n\t},\n\n\tsnapToGrid: function(pos) {\n\t\tvar cell = this.grid.pixelToCell(pos);\n\t\tpos.copy(this.grid.cellToPixel(cell));\n\t},\n\n\tsnapTileToGrid: function(tile) {\n\t\tif (tile.cell) {\n\t\t\ttile.position.copy(this.grid.cellToPixel(tile.cell));\n\t\t}\n\t\telse {\n\t\t\tvar cell = this.grid.pixelToCell(tile.position);\n\t\t\ttile.position.copy(this.grid.cellToPixel(cell));\n\t\t}\n\t\treturn tile;\n\t},\n\n\tgetRandomTile: function() {\n\t\tvar i = vg.Tools.randomInt(0, this.tiles.length-1);\n\t\treturn this.tiles[i];\n\t},\n\n\tfindPath: function(startTile, endTile, heuristic) {\n\t\treturn this.finder.findPath(startTile.cell, endTile.cell, heuristic, this.grid);\n\t},\n\n\tsetGrid: function(newGrid) {\n\t\tthis.group.remove(this.tileGroup);\n\t\tif (this.grid && newGrid !== this.grid) {\n\t\t\tthis.removeAllTiles();\n\t\t\tthis.tiles.forEach(function(t) {\n\t\t\t\tthis.grid.remove(t.cell);\n\t\t\t\tt.dispose();\n\t\t\t});\n\t\t\tthis.grid.dispose();\n\t\t}\n\t\tthis.grid = newGrid;\n\t\tthis.tiles = [];\n\t\tthis.tileGroup = new THREE.Object3D();\n\t\tthis.group.add(this.tileGroup);\n\t},\n\n\tgenerateOverlay: function(size) {\n\t\tvar mat = new THREE.LineBasicMaterial({\n\t\t\tcolor: 0x000000,\n\t\t\topacity: 0.3\n\t\t});\n\n\t\tif (this.overlay) {\n\t\t\tthis.group.remove(this.overlay);\n\t\t}\n\n\t\tthis.overlay = new THREE.Object3D();\n\n\t\tthis.grid.generateOverlay(size, this.overlay, mat);\n\n\t\tthis.group.add(this.overlay);\n\t},\n\n\tgenerateTilemap: function(config) {\n\t\tthis.reset();\n\n\t\tvar tiles = this.grid.generateTiles(config);\n\t\tthis.tiles = tiles;\n\n\t\tthis.tileGroup = new THREE.Object3D();\n\t\tfor (var i = 0; i < tiles.length; i++) {\n\t\t\tthis.tileGroup.add(tiles[i].mesh);\n\t\t}\n\n\t\tthis.group.add(this.tileGroup);\n\t},\n\n\treset: function() {\n\t\t// removes all tiles from the scene, but leaves the grid intact\n\t\tthis.removeAllTiles();\n\t\tif (this.tileGroup) this.group.remove(this.tileGroup);\n\t}\n};\n\nvg.Board.prototype.constructor = vg.Board;\n","/*\n\tSimple structure for holding grid coordinates and extra data about them.\n\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n*/\nvg.Cell = function(q, r, s, h) {\n\tthis.q = q || 0; // x grid coordinate (using different letters so that it won't be confused with pixel/world coordinates)\n\tthis.r = r || 0; // y grid coordinate\n\tthis.s = s || 0; // z grid coordinate\n\tthis.h = h || 1; // 3D height of the cell, used by visual representation and pathfinder, cannot be less than 1\n\tthis.tile = null; // optional link to the visual representation's class instance\n\tthis.userData = {}; // populate with any extra data needed in your game\n\tthis.walkable = true; // if true, pathfinder will use as a through node\n\t// rest of these are used by the pathfinder and overwritten at runtime, so don't touch\n\tthis._calcCost = 0;\n\tthis._priority = 0;\n\tthis._visited = false;\n\tthis._parent = null;\n\tthis.uniqueID = vg.LinkedList.generateID();\n};\n\nvg.Cell.prototype = {\n\tset: function(q, r, s) {\n\t\tthis.q = q;\n\t\tthis.r = r;\n\t\tthis.s = s;\n\t\treturn this;\n\t},\n\n\tcopy: function(cell) {\n\t\tthis.q = cell.q;\n\t\tthis.r = cell.r;\n\t\tthis.s = cell.s;\n\t\tthis.h = cell.h;\n\t\tthis.tile = cell.tile || null;\n\t\tthis.userData = cell.userData || {};\n\t\tthis.walkable = cell.walkable;\n\t\treturn this;\n\t},\n\n\tadd: function(cell) {\n\t\tthis.q += cell.q;\n\t\tthis.r += cell.r;\n\t\tthis.s += cell.s;\n\t\treturn this;\n\t},\n\n\tequals: function(cell) {\n\t\treturn this.q === cell.q && this.r === cell.r && this.s === cell.s;\n\t}\n};\n\nvg.Cell.prototype.constructor = vg.Cell;\n","/*\n\tGraph of hexagons. Handles grid cell management (placement math for eg pathfinding, range, etc) and grid conversion math.\n\t[Cube/axial coordinate system](http://www.redblobgames.com/grids/hexagons/), \"flat top\" version only. Since this is 3D, just rotate your camera for pointy top maps.\n\tInterface:\n\ttype\n\tsize - number of cells (in radius); only used if the map is generated\n\tcellSize\n\tcells - a hash so we can have sparse maps\n\tnumCells\n\textrudeSettings\n\tautogenerated\n\tcellShape\n\tcellGeo\n\tcellShapeGeo\n\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n */\n// 'utils/Loader', 'graphs/Hex', 'utils/Tools'\nvg.HexGrid = function(config) {\n\tconfig = config || {};\n\t/* ______________________________________________\n\t\tGRID INTERFACE:\n\t*/\n\tthis.type = vg.HEX;\n\tthis.size = 5; // only used for generated maps\n\tthis.cellSize = typeof config.cellSize === 'undefined' ? 10 : config.cellSize;\n\tthis.cells = {};\n\tthis.numCells = 0;\n\n\tthis.extrudeSettings = null;\n\tthis.autogenerated = false;\n\n\t// create base shape used for building geometry\n\tvar i, verts = [];\n\t// create the skeleton of the hex\n\tfor (i = 0; i < 6; i++) {\n\t\tverts.push(this._createVertex(i));\n\t}\n\t// copy the verts into a shape for the geometry to use\n\tthis.cellShape = new THREE.Shape();\n\tthis.cellShape.moveTo(verts[0].x, verts[0].y);\n\tfor (i = 1; i < 6; i++) {\n\t\tthis.cellShape.lineTo(verts[i].x, verts[i].y);\n\t}\n\tthis.cellShape.lineTo(verts[0].x, verts[0].y);\n\tthis.cellShape.autoClose = true;\n\n\tthis.cellGeo = new THREE.Geometry();\n\tthis.cellGeo.vertices = verts;\n\tthis.cellGeo.verticesNeedUpdate = true;\n\n\tthis.cellShapeGeo = new THREE.ShapeGeometry(this.cellShape);\n\n\t/* ______________________________________________\n\t\tPRIVATE\n\t*/\n\n\tthis._cellWidth = this.cellSize * 2;\n\tthis._cellLength = (vg.SQRT3 * 0.5) * this._cellWidth;\n\tthis._hashDelimeter = '.';\n\t// pre-computed permutations\n\tthis._directions = [new vg.Cell(+1, -1, 0), new vg.Cell(+1, 0, -1), new vg.Cell(0, +1, -1),\n\t\t\t\t\t\tnew vg.Cell(-1, +1, 0), new vg.Cell(-1, 0, +1), new vg.Cell(0, -1, +1)];\n\tthis._diagonals = [new vg.Cell(+2, -1, -1), new vg.Cell(+1, +1, -2), new vg.Cell(-1, +2, -1),\n\t\t\t\t\t new vg.Cell(-2, +1, +1), new vg.Cell(-1, -1, +2), new vg.Cell(+1, -2, +1)];\n\t// cached objects\n\tthis._list = [];\n\tthis._vec3 = new THREE.Vector3();\n\tthis._cel = new vg.Cell();\n\tthis._conversionVec = new THREE.Vector3();\n\tthis._geoCache = [];\n\tthis._matCache = [];\n};\n\nvg.HexGrid.TWO_THIRDS = 2 / 3;\n\nvg.HexGrid.prototype = {\n\t/* ________________________________________________________________________\n\t\tHigh-level functions that the Board interfaces with (all grids implement)\n\t */\n\n\t// grid cell (Hex in cube coordinate space) to position in pixels/world\n\tcellToPixel: function(cell) {\n\t\tthis._vec3.x = cell.q * this._cellWidth * 0.75;\n\t\tthis._vec3.y = cell.h;\n\t\tthis._vec3.z = -((cell.s - cell.r) * this._cellLength * 0.5);\n\t\treturn this._vec3;\n\t},\n\n\tpixelToCell: function(pos) {\n\t\t// convert a position in world space (\"pixels\") to cell coordinates\n\t\tvar q = pos.x * (vg.HexGrid.TWO_THIRDS / this.cellSize);\n\t\tvar r = ((-pos.x / 3) + (vg.SQRT3/3) * pos.z) / this.cellSize;\n\t\tthis._cel.set(q, r, -q-r);\n\t\treturn this._cubeRound(this._cel);\n\t},\n\n\tgetCellAt: function(pos) {\n\t\t// get the Cell (if any) at the passed world position\n\t\tvar q = pos.x * (vg.HexGrid.TWO_THIRDS / this.cellSize);\n\t\tvar r = ((-pos.x / 3) + (vg.SQRT3/3) * pos.z) / this.cellSize;\n\t\tthis._cel.set(q, r, -q-r);\n\t\tthis._cubeRound(this._cel);\n\t\treturn this.cells[this.cellToHash(this._cel)];\n\t},\n\n\tgetNeighbors: function(cell, diagonal, filter) {\n\t\t// always returns an array\n\t\tvar i, n, l = this._directions.length;\n\t\tthis._list.length = 0;\n\t\tfor (i = 0; i < l; i++) {\n\t\t\tthis._cel.copy(cell);\n\t\t\tthis._cel.add(this._directions[i]);\n\t\t\tn = this.cells[this.cellToHash(this._cel)];\n\t\t\tif (!n || (filter && !filter(cell, n))) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tthis._list.push(n);\n\t\t}\n\t\tif (diagonal) {\n\t\t\tfor (i = 0; i < l; i++) {\n\t\t\t\tthis._cel.copy(cell);\n\t\t\t\tthis._cel.add(this._diagonals[i]);\n\t\t\t\tn = this.cells[this.cellToHash(this._cel)];\n\t\t\t\tif (!n || (filter && !filter(cell, n))) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tthis._list.push(n);\n\t\t\t}\n\t\t}\n\t\treturn this._list;\n\t},\n\n\tgetRandomCell: function() {\n\t\tvar c, i = 0, x = vg.Tools.randomInt(0, this.numCells);\n\t\tfor (c in this.cells) {\n\t\t\tif (i === x) {\n\t\t\t\treturn this.cells[c];\n\t\t\t}\n\t\t\ti++;\n\t\t}\n\t\treturn this.cells[c];\n\t},\n\n\tcellToHash: function(cell) {\n\t\treturn cell.q+this._hashDelimeter+cell.r+this._hashDelimeter+cell.s;\n\t},\n\n\tdistance: function(cellA, cellB) {\n\t\tvar d = Math.max(Math.abs(cellA.q - cellB.q), Math.abs(cellA.r - cellB.r), Math.abs(cellA.s - cellB.s));\n\t\td += cellB.h - cellA.h; // include vertical height\n\t\treturn d;\n\t},\n\n\tclearPath: function() {\n\t\tvar i, c;\n\t\tfor (i in this.cells) {\n\t\t\tc = this.cells[i];\n\t\t\tc._calcCost = 0;\n\t\t\tc._priority = 0;\n\t\t\tc._parent = null;\n\t\t\tc._visited = false;\n\t\t}\n\t},\n\n\ttraverse: function(cb) {\n\t\tvar i;\n\t\tfor (i in this.cells) {\n\t\t\tcb(this.cells[i]);\n\t\t}\n\t},\n\n\tgenerateTile: function(cell, scale, material) {\n\t\tvar height = Math.abs(cell.h);\n\t\tif (height < 1) height = 1;\n\n\t\tvar geo = this._geoCache[height];\n\t\tif (!geo) {\n\t\t\tthis.extrudeSettings.amount = height;\n\t\t\tgeo = new THREE.ExtrudeGeometry(this.cellShape, this.extrudeSettings);\n\t\t\tthis._geoCache[height] = geo;\n\t\t}\n\n\t\t/*mat = this._matCache[c.matConfig.mat_cache_id];\n\t\tif (!mat) { // MaterialLoader? we currently only support basic stuff though. maybe later\n\t\t\tmat.map = Loader.loadTexture(c.matConfig.imgURL);\n\t\t\tdelete c.matConfig.imgURL;\n\t\t\tmat = new THREE[c.matConfig.type](c.matConfig);\n\t\t\tthis._matCache[c.matConfig.mat_cache_id] = mat;\n\t\t}*/\n\n\t\tvar tile = new vg.Tile({\n\t\t\tsize: this.cellSize,\n\t\t\tscale: scale,\n\t\t\tcell: cell,\n\t\t\tgeometry: geo,\n\t\t\tmaterial: material\n\t\t});\n\n\t\tcell.tile = tile;\n\n\t\treturn tile;\n\t},\n\n\tgenerateTiles: function(config) {\n\t\tconfig = config || {};\n\t\tvar tiles = [];\n\t\tvar settings = {\n\t\t\ttileScale: 0.95,\n\t\t\tcellSize: this.cellSize,\n\t\t\tmaterial: null,\n\t\t\textrudeSettings: {\n\t\t\t\tamount: 1,\n\t\t\t\tbevelEnabled: true,\n\t\t\t\tbevelSegments: 1,\n\t\t\t\tsteps: 1,\n\t\t\t\tbevelSize: 0.5,\n\t\t\t\tbevelThickness: 0.5\n\t\t\t}\n\t\t}\n\t\tsettings = vg.Tools.merge(settings, config);\n\n\t\t/*if (!settings.material) {\n\t\t\tsettings.material = new THREE.MeshPhongMaterial({\n\t\t\t\tcolor: vg.Tools.randomizeRGB('30, 30, 30', 10)\n\t\t\t});\n\t\t}*/\n\n\t\t// overwrite with any new dimensions\n\t\tthis.cellSize = settings.cellSize;\n\t\tthis._cellWidth = this.cellSize * 2;\n\t\tthis._cellLength = (vg.SQRT3 * 0.5) * this._cellWidth;\n\n\t\tthis.autogenerated = true;\n\t\tthis.extrudeSettings = settings.extrudeSettings;\n\n\t\tvar i, t, c;\n\t\tfor (i in this.cells) {\n\t\t\tc = this.cells[i];\n\t\t\tt = this.generateTile(c, settings.tileScale, settings.material);\n\t\t\tt.position.copy(this.cellToPixel(c));\n\t\t\tt.position.y = 0;\n\t\t\ttiles.push(t);\n\t\t}\n\t\treturn tiles;\n\t},\n\n\tgenerateTilePoly: function(material) {\n\t\tif (!material) {\n\t\t\tmaterial = new THREE.MeshBasicMaterial({color: 0x24b4ff});\n\t\t}\n\t\tvar mesh = new THREE.Mesh(this.cellShapeGeo, material);\n\t\tthis._vec3.set(1, 0, 0);\n\t\tmesh.rotateOnAxis(this._vec3, vg.PI/2);\n\t\treturn mesh;\n\t},\n\n\t// create a flat, hexagon-shaped grid\n\tgenerate: function(config) {\n\t\tconfig = config || {};\n\t\tthis.size = typeof config.size === 'undefined' ? this.size : config.size;\n\t\tvar x, y, z, c;\n\t\tfor (x = -this.size; x < this.size+1; x++) {\n\t\t\tfor (y = -this.size; y < this.size+1; y++) {\n\t\t\t\tz = -x-y;\n\t\t\t\tif (Math.abs(x) <= this.size && Math.abs(y) <= this.size && Math.abs(z) <= this.size) {\n\t\t\t\t\tc = new vg.Cell(x, y, z);\n\t\t\t\t\tthis.add(c);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t},\n\n\tgenerateOverlay: function(size, overlayObj, overlayMat) {\n\t\tvar x, y, z;\n\t\tvar geo = this.cellShape.createPointsGeometry();\n\t\tfor (x = -size; x < size+1; x++) {\n\t\t\tfor (y = -size; y < size+1; y++) {\n\t\t\t\tz = -x-y;\n\t\t\t\tif (Math.abs(x) <= size && Math.abs(y) <= size && Math.abs(z) <= size) {\n\t\t\t\t\tthis._cel.set(x, y, z); // define the cell\n\t\t\t\t\tvar line = new THREE.Line(geo, overlayMat);\n\t\t\t\t\tline.position.copy(this.cellToPixel(this._cel));\n\t\t\t\t\tline.rotation.x = 90 * vg.DEG_TO_RAD;\n\t\t\t\t\toverlayObj.add(line);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t},\n\n\tadd: function(cell) {\n\t\tvar h = this.cellToHash(cell);\n\t\tif (this.cells[h]) {\n\t\t\t// console.warn('A cell already exists there');\n\t\t\treturn;\n\t\t}\n\t\tthis.cells[h] = cell;\n\t\tthis.numCells++;\n\n\t\treturn cell;\n\t},\n\n\tremove: function(cell) {\n\t\tvar h = this.cellToHash(cell);\n\t\tif (this.cells[h]) {\n\t\t\tdelete this.cells[h];\n\t\t\tthis.numCells--;\n\t\t}\n\t},\n\n\tdispose: function() {\n\t\tthis.cells = null;\n\t\tthis.numCells = 0;\n\t\tthis.cellShape = null;\n\t\tthis.cellGeo.dispose();\n\t\tthis.cellGeo = null;\n\t\tthis.cellShapeGeo.dispose();\n\t\tthis.cellShapeGeo = null;\n\t\tthis._list = null;\n\t\tthis._vec3 = null;\n\t\tthis._conversionVec = null;\n\t\tthis._geoCache = null;\n\t\tthis._matCache = null;\n\t},\n\n\t/*\n\t\tLoad a grid from a parsed json object.\n\t\tjson = {\n\t\t\textrudeSettings,\n\t\t\tsize,\n\t\t\tcellSize,\n\t\t\tautogenerated,\n\t\t\tcells: [],\n\t\t\tmaterials: [\n\t\t\t\t{\n\t\t\t\t\tcache_id: 0,\n\t\t\t\t\ttype: 'MeshLambertMaterial',\n\t\t\t\t\tcolor, ambient, emissive, reflectivity, refractionRatio, wrapAround,\n\t\t\t\t\timgURL: url\n\t\t\t\t},\n\t\t\t\t{\n\t\t\t\t\tcacheId: 1, ...\n\t\t\t\t}\n\t\t\t\t...\n\t\t\t]\n\t\t}\n\t*/\n\tload: function(url, cb, scope) {\n\t\tvar self = this;\n\t\tvg.Tools.getJSON({\n\t\t\turl: url,\n\t\t\tcallback: function(json) {\n\t\t\t\tself.fromJSON(json);\n\t\t\t\tcb.call(scope || null, json);\n\t\t\t},\n\t\t\tcache: false,\n\t\t\tscope: self\n\t\t});\n\t},\n\n\tfromJSON: function(json) {\n\t\tvar i, c;\n\t\tvar cells = json.cells;\n\n\t\tthis.cells = {};\n\t\tthis.numCells = 0;\n\n\t\tthis.size = json.size;\n\t\tthis.cellSize = json.cellSize;\n\t\tthis._cellWidth = this.cellSize * 2;\n\t\tthis._cellLength = (vg.SQRT3 * 0.5) * this._cellWidth;\n\n\t\tthis.extrudeSettings = json.extrudeSettings;\n\t\tthis.autogenerated = json.autogenerated;\n\n\t\tfor (i = 0; i < cells.length; i++) {\n\t\t\tc = new vg.Cell();\n\t\t\tc.copy(cells[i]);\n\t\t\tthis.add(c);\n\t\t}\n\t},\n\n\ttoJSON: function() {\n\t\tvar json = {\n\t\t\tsize: this.size,\n\t\t\tcellSize: this.cellSize,\n\t\t\textrudeSettings: this.extrudeSettings,\n\t\t\tautogenerated: this.autogenerated\n\t\t};\n\t\tvar cells = [];\n\t\tvar c, k;\n\n\t\tfor (k in this.cells) {\n\t\t\tc = this.cells[k];\n\t\t\tcells.push({\n\t\t\t\tq: c.q,\n\t\t\t\tr: c.r,\n\t\t\t\ts: c.s,\n\t\t\t\th: c.h,\n\t\t\t\twalkable: c.walkable,\n\t\t\t\tuserData: c.userData\n\t\t\t});\n\t\t}\n\t\tjson.cells = cells;\n\n\t\treturn json;\n\t},\n\n\t/* ________________________________________________________________________\n\t\tHexagon-specific conversion math\n\t\tMostly commented out because they're inlined whenever possible to increase performance.\n\t\tThey're still here for reference.\n\t */\n\n\t_createVertex: function(i) {\n\t\tvar angle = (vg.TAU / 6) * i;\n\t\treturn new THREE.Vector3((this.cellSize * Math.cos(angle)), (this.cellSize * Math.sin(angle)), 0);\n\t},\n\n\t/*_pixelToAxial: function(pos) {\n\t\tvar q, r; // = x, y\n\t\tq = pos.x * ((2/3) / this.cellSize);\n\t\tr = ((-pos.x / 3) + (vg.SQRT3/3) * pos.y) / this.cellSize;\n\t\tthis._cel.set(q, r, -q-r);\n\t\treturn this._cubeRound(this._cel);\n\t},*/\n\n\t/*_axialToCube: function(h) {\n\t\treturn {\n\t\t\tq: h.q,\n\t\t\tr: h.r,\n\t\t\ts: -h.q - h.r\n\t\t};\n\t},*/\n\n\t/*_cubeToAxial: function(cell) {\n\t\treturn cell; // yep\n\t},*/\n\n\t/*_axialToPixel: function(cell) {\n\t\tvar x, y; // = q, r\n\t\tx = cell.q * this._cellWidth * 0.75;\n\t\ty = (cell.s - cell.r) * this._cellLength * 0.5;\n\t\treturn {x: x, y: -y};\n\t},*/\n\n\t/*_hexToPixel: function(h) {\n\t\tvar x, y; // = q, r\n\t\tx = this.cellSize * 1.5 * h.x;\n\t\ty = this.cellSize * vg.SQRT3 * (h.y + (h.x * 0.5));\n\t\treturn {x: x, y: y};\n\t},*/\n\n\t/*_axialRound: function(h) {\n\t\treturn this._cubeRound(this.axialToCube(h));\n\t},*/\n\n\t_cubeRound: function(h) {\n\t\tvar rx = Math.round(h.q);\n\t\tvar ry = Math.round(h.r);\n\t\tvar rz = Math.round(h.s);\n\n\t\tvar xDiff = Math.abs(rx - h.q);\n\t\tvar yDiff = Math.abs(ry - h.r);\n\t\tvar zDiff = Math.abs(rz - h.s);\n\n\t\tif (xDiff > yDiff && xDiff > zDiff) {\n\t\t\trx = -ry-rz;\n\t\t}\n\t\telse if (yDiff > zDiff) {\n\t\t\try = -rx-rz;\n\t\t}\n\t\telse {\n\t\t\trz = -rx-ry;\n\t\t}\n\n\t\treturn this._cel.set(rx, ry, rz);\n\t},\n\n\t/*_cubeDistance: function(a, b) {\n\t\treturn Math.max(Math.abs(a.q - b.q), Math.abs(a.r - b.r), Math.abs(a.s - b.s));\n\t}*/\n};\n\nvg.HexGrid.prototype.constructor = vg.HexGrid;\n","/*\n\tGraph of squares. Handles grid cell management (placement math for eg pathfinding, range, etc) and grid conversion math.\n\tInterface:\n\ttype\n\tsize - number of cells (in radius); only used if the map is generated\n\tcellSize\n\tcells - a hash so we can have sparse maps\n\tnumCells\n\textrudeSettings\n\tautogenerated\n\tcellShape\n\tcellGeo\n\tcellShapeGeo\n\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n */\nvg.SqrGrid = function(config) {\n\tconfig = config || {};\n\t/* ______________________________________________\n\t\tGRID INTERFACE:\n\t*/\n\tthis.type = vg.SQR;\n\tthis.size = 5; // only used for generated maps\n\tthis.cellSize = typeof config.cellSize === 'undefined' ? 10 : config.cellSize;\n\tthis.cells = {};\n\tthis.numCells = 0;\n\n\tthis.extrudeSettings = null;\n\tthis.autogenerated = false;\n\n\t// create base shape used for building geometry\n\tvar verts = [];\n\tverts.push(new THREE.Vector3());\n\tverts.push(new THREE.Vector3(-this.cellSize, this.cellSize));\n\tverts.push(new THREE.Vector3(this.cellSize, this.cellSize));\n\tverts.push(new THREE.Vector3(this.cellSize, -this.cellSize));\n\t// copy the verts into a shape for the geometry to use\n\tthis.cellShape = new THREE.Shape();\n\tthis.cellShape.moveTo(-this.cellSize, -this.cellSize);\n\tthis.cellShape.lineTo(-this.cellSize, this.cellSize);\n\tthis.cellShape.lineTo(this.cellSize, this.cellSize);\n\tthis.cellShape.lineTo(this.cellSize, -this.cellSize);\n\tthis.cellShape.lineTo(-this.cellSize, -this.cellSize);\n\n\tthis.cellGeo = new THREE.Geometry();\n\tthis.cellGeo.vertices = verts;\n\tthis.cellGeo.verticesNeedUpdate = true;\n\n\tthis.cellShapeGeo = new THREE.ShapeGeometry(this.cellShape);\n\n\t/* ______________________________________________\n\t\tPRIVATE\n\t*/\n\n\tthis._fullCellSize = this.cellSize * 2;\n\tthis._hashDelimeter = '.';\n\t// pre-computed permutations\n\tthis._directions = [new vg.Cell(+1, 0, 0), new vg.Cell(0, -1, 0),\n\t\t\t\t\t\tnew vg.Cell(-1, 0, 0), new vg.Cell(0, +1, 0)];\n\tthis._diagonals = [new vg.Cell(-1, -1, 0), new vg.Cell(-1, +1, 0),\n\t\t\t\t\t new vg.Cell(+1, +1, 0), new vg.Cell(+1, -1, 0)];\n\t// cached objects\n\tthis._list = [];\n\tthis._vec3 = new THREE.Vector3();\n\tthis._cel = new vg.Cell();\n\tthis._conversionVec = new THREE.Vector3();\n\tthis._geoCache = [];\n\tthis._matCache = [];\n};\n\nvg.SqrGrid.prototype = {\n\t/*\n\t\t________________________________________________________________________\n\t\tHigh-level functions that the Board interfaces with (all grids implement)\n\t */\n\n\tcellToPixel: function(cell) {\n\t\tthis._vec3.x = cell.q * this._fullCellSize;\n\t\tthis._vec3.y = cell.h;\n\t\tthis._vec3.z = cell.r * this._fullCellSize;\n\t\treturn this._vec3;\n\t},\n\n\tpixelToCell: function(pos) {\n\t\tvar q = Math.round(pos.x / this._fullCellSize);\n\t\tvar r = Math.round(pos.z / this._fullCellSize);\n\t\treturn this._cel.set(q, r, 0);\n\t},\n\n\tgetCellAt: function(pos) {\n\t\tvar q = Math.round(pos.x / this._fullCellSize);\n\t\tvar r = Math.round(pos.z / this._fullCellSize);\n\t\tthis._cel.set(q, r);\n\t\treturn this.cells[this.cellToHash(this._cel)];\n\t},\n\n\tgetNeighbors: function(cell, diagonal, filter) {\n\t\t// always returns an array\n\t\tvar i, n, l = this._directions.length;\n\t\tthis._list.length = 0;\n\t\tfor (i = 0; i < l; i++) {\n\t\t\tthis._cel.copy(cell);\n\t\t\tthis._cel.add(this._directions[i]);\n\t\t\tn = this.cells[this.cellToHash(this._cel)];\n\t\t\tif (!n || (filter && !filter(cell, n))) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tthis._list.push(n);\n\t\t}\n\t\tif (diagonal) {\n\t\t\tfor (i = 0; i < l; i++) {\n\t\t\t\tthis._cel.copy(cell);\n\t\t\t\tthis._cel.add(this._diagonals[i]);\n\t\t\t\tn = this.cells[this.cellToHash(this._cel)];\n\t\t\t\tif (!n || (filter && !filter(cell, n))) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tthis._list.push(n);\n\t\t\t}\n\t\t}\n\t\treturn this._list;\n\t},\n\n\tgetRandomCell: function() {\n\t\tvar c, i = 0, x = vg.Tools.randomInt(0, this.numCells);\n\t\tfor (c in this.cells) {\n\t\t\tif (i === x) {\n\t\t\t\treturn this.cells[c];\n\t\t\t}\n\t\t\ti++;\n\t\t}\n\t\treturn this.cells[c];\n\t},\n\n\tcellToHash: function(cell) {\n\t\treturn cell.q+this._hashDelimeter+cell.r; // s is not used in a square grid\n\t},\n\n\tdistance: function(cellA, cellB) {\n\t\tvar d = Math.max(Math.abs(cellA.q - cellB.q), Math.abs(cellA.r - cellB.r));\n\t\td += cellB.h - cellA.h; // include vertical size\n\t\treturn d;\n\t},\n\n\tclearPath: function() {\n\t\tvar i, c;\n\t\tfor (i in this.cells) {\n\t\t\tc = this.cells[i];\n\t\t\tc._calcCost = 0;\n\t\t\tc._priority = 0;\n\t\t\tc._parent = null;\n\t\t\tc._visited = false;\n\t\t}\n\t},\n\n\ttraverse: function(cb) {\n\t\tvar i;\n\t\tfor (i in this.cells) {\n\t\t\tcb(this.cells[i]);\n\t\t}\n\t},\n\n\tgenerateTile: function(cell, scale, material) {\n\t\tvar height = Math.abs(cell.h);\n\t\tif (height < 1) height = 1;\n\n\t\tvar geo = this._geoCache[height];\n\t\tif (!geo) {\n\t\t\tthis.extrudeSettings.amount = height;\n\t\t\tgeo = new THREE.ExtrudeGeometry(this.cellShape, this.extrudeSettings);\n\t\t\tthis._geoCache[height] = geo;\n\t\t}\n\n\t\t/*mat = this._matCache[c.matConfig.mat_cache_id];\n\t\tif (!mat) { // MaterialLoader? we currently only support basic stuff though. maybe later\n\t\t\tmat.map = Loader.loadTexture(c.matConfig.imgURL);\n\t\t\tdelete c.matConfig.imgURL;\n\t\t\tmat = new THREE[c.matConfig.type](c.matConfig);\n\t\t\tthis._matCache[c.matConfig.mat_cache_id] = mat;\n\t\t}*/\n\n\t\tvar t = new vg.Tile({\n\t\t\tsize: this.cellSize,\n\t\t\tscale: scale,\n\t\t\tcell: cell,\n\t\t\tgeometry: geo,\n\t\t\tmaterial: material\n\t\t});\n\n\t\tcell.tile = t;\n\n\t\treturn t;\n\t},\n\n\tgenerateTiles: function(config) {\n\t\tconfig = config || {};\n\t\tvar tiles = [];\n\t\tvar settings = {\n\t\t\ttileScale: 0.95,\n\t\t\tcellSize: this.cellSize,\n\t\t\tmaterial: null,\n\t\t\textrudeSettings: {\n\t\t\t\tamount: 1,\n\t\t\t\tbevelEnabled: true,\n\t\t\t\tbevelSegments: 1,\n\t\t\t\tsteps: 1,\n\t\t\t\tbevelSize: 0.5,\n\t\t\t\tbevelThickness: 0.5\n\t\t\t}\n\t\t}\n\t\tsettings = vg.Tools.merge(settings, config);\n\n\t\t/*if (!settings.material) {\n\t\t\tsettings.material = new THREE.MeshPhongMaterial({\n\t\t\t\tcolor: vg.Tools.randomizeRGB('30, 30, 30', 10)\n\t\t\t});\n\t\t}*/\n\n\t\t// overwrite with any new dimensions\n\t\tthis.cellSize = settings.cellSize;\n\t\tthis._fullCellSize = this.cellSize * 2;\n\n\t\tthis.autogenerated = true;\n\t\tthis.extrudeSettings = settings.extrudeSettings;\n\n\t\tvar i, t, c;\n\t\tfor (i in this.cells) {\n\t\t\tc = this.cells[i];\n\t\t\tt = this.generateTile(c, settings.tileScale, settings.material);\n\t\t\tt.position.copy(this.cellToPixel(c));\n\t\t\tt.position.y = 0;\n\t\t\ttiles.push(t);\n\t\t}\n\t\treturn tiles;\n\t},\n\n\tgenerateTilePoly: function(material) {\n\t\tif (!material) {\n\t\t\tmaterial = new THREE.MeshBasicMaterial({color: 0x24b4ff});\n\t\t}\n\t\tvar mesh = new THREE.Mesh(this.cellShapeGeo, material);\n\t\tthis._vec3.set(1, 0, 0);\n\t\tmesh.rotateOnAxis(this._vec3, vg.PI/2);\n\t\treturn mesh;\n\t},\n\n\t// create a flat, square-shaped grid\n\tgenerate: function(config) {\n\t\tconfig = config || {};\n\t\tthis.size = typeof config.size === 'undefined' ? this.size : config.size;\n\t\tvar x, y, c;\n\t\tvar half = Math.ceil(this.size / 2);\n\t\tfor (x = -half; x < half; x++) {\n\t\t\tfor (y = -half; y < half; y++) {\n\t\t\t\tc = new vg.Cell(x, y + 1);\n\t\t\t\tthis.add(c);\n\t\t\t}\n\t\t}\n\t},\n\n\tgenerateOverlay: function(size, overlayObj, overlayMat) {\n\t\tvar x, y;\n\t\tvar half = Math.ceil(size / 2);\n\t\tfor (x = -half; x < half; x++) {\n\t\t\tfor (y = -half; y < half; y++) {\n\t\t\t\tthis._cel.set(x, y); // define the cell\n\t\t\t\tvar line = new THREE.Line(this.cellGeo, overlayMat);\n\t\t\t\tline.position.copy(this.cellToPixel(this._cel));\n\t\t\t\tline.rotation.x = 90 * vg.DEG_TO_RAD;\n\t\t\t\toverlayObj.add(line);\n\t\t\t}\n\t\t}\n\t},\n\n\tadd: function(cell) {\n\t\tvar h = this.cellToHash(cell);\n\t\tif (this.cells[h]) {\n\t\t\t// console.warn('A cell already exists there');\n\t\t\treturn;\n\t\t}\n\t\tthis.cells[h] = cell;\n\t\tthis.numCells++;\n\n\t\treturn cell;\n\t},\n\n\tremove: function(cell) {\n\t\tvar h = this.cellToHash(cell);\n\t\tif (this.cells[h]) {\n\t\t\tdelete this.cells[h];\n\t\t\tthis.numCells--;\n\t\t}\n\t},\n\n\tdispose: function() {\n\t\tthis.cells = null;\n\t\tthis.numCells = 0;\n\t\tthis.cellShape = null;\n\t\tthis.cellGeo.dispose();\n\t\tthis.cellGeo = null;\n\t\tthis.cellShapeGeo.dispose();\n\t\tthis.cellShapeGeo = null;\n\t\tthis._list = null;\n\t\tthis._vec3 = null;\n\t\tthis._conversionVec = null;\n\t\tthis._geoCache = null;\n\t\tthis._matCache = null;\n\t},\n\n\t/*\n\t\tLoad a grid from a parsed json object.\n\t\tjson = {\n\t\t\textrudeSettings,\n\t\t\tsize,\n\t\t\tcellSize,\n\t\t\tautogenerated,\n\t\t\tcells: [],\n\t\t\tmaterials: [\n\t\t\t\t{\n\t\t\t\t\tcache_id: 0,\n\t\t\t\t\ttype: 'MeshLambertMaterial',\n\t\t\t\t\tcolor, ambient, emissive, reflectivity, refractionRatio, wrapAround,\n\t\t\t\t\timgURL: url\n\t\t\t\t},\n\t\t\t\t{\n\t\t\t\t\tcacheId: 1, ...\n\t\t\t\t}\n\t\t\t\t...\n\t\t\t]\n\t\t}\n\t*/\n\tload: function(url, callback, scope) {\n\t\tvg.Tools.getJSON({\n\t\t\turl: url,\n\t\t\tcallback: function(json) {\n\t\t\t\tthis.fromJSON(json);\n\t\t\t\tcallback.call(scope || null, json);\n\t\t\t},\n\t\t\tcache: false,\n\t\t\tscope: this\n\t\t});\n\t},\n\n\tfromJSON: function(json) {\n\t\tvar i, c;\n\t\tvar cells = json.cells;\n\n\t\tthis.cells = {};\n\t\tthis.numCells = 0;\n\n\t\tthis.size = json.size;\n\t\tthis.cellSize = json.cellSize;\n\t\tthis._fullCellSize = this.cellSize * 2;\n\t\tthis.extrudeSettings = json.extrudeSettings;\n\t\tthis.autogenerated = json.autogenerated;\n\n\t\tfor (i = 0; i < cells.length; i++) {\n\t\t\tc = new vg.Cell();\n\t\t\tc.copy(cells[i]);\n\t\t\tthis.add(c);\n\t\t}\n\t},\n\n\ttoJSON: function() {\n\t\tvar json = {\n\t\t\tsize: this.size,\n\t\t\tcellSize: this.cellSize,\n\t\t\textrudeSettings: this.extrudeSettings,\n\t\t\tautogenerated: this.autogenerated\n\t\t};\n\t\tvar cells = [];\n\t\tvar c, k;\n\n\t\tfor (k in this.cells) {\n\t\t\tc = this.cells[k];\n\t\t\tcells.push({\n\t\t\t\tq: c.q,\n\t\t\t\tr: c.r,\n\t\t\t\ts: c.s,\n\t\t\t\th: c.h,\n\t\t\t\twalkable: c.walkable,\n\t\t\t\tuserData: c.userData\n\t\t\t});\n\t\t}\n\t\tjson.cells = cells;\n\n\t\treturn json;\n\t}\n};\n\nvg.SqrGrid.prototype.constructor = vg.SqrGrid;\n","/*\n\tExample tile class that constructs its geometry for rendering and holds some gameplay properties.\n\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n*/\nvg.Tile = function(config) {\n\tconfig = config || {};\n\tvar settings = {\n\t\tcell: null, // required vg.Cell\n\t\tgeometry: null, // required threejs geometry\n\t\tmaterial: null // not required but it would improve performance significantly\n\t};\n\tsettings = vg.Tools.merge(settings, config);\n\n\tif (!settings.cell || !settings.geometry) {\n\t\tthrow new Error('Missing vg.Tile configuration');\n\t}\n\n\tthis.cell = settings.cell;\n\tif (this.cell.tile && this.cell.tile !== this) this.cell.tile.dispose(); // remove whatever was there\n\tthis.cell.tile = this;\n\n\tthis.uniqueID = vg.Tools.generateID();\n\n\tthis.geometry = settings.geometry;\n\tthis.material = settings.material;\n\tif (!this.material) {\n\t\tthis.material = new THREE.MeshPhongMaterial({\n\t\t\tcolor: vg.Tools.randomizeRGB('30, 30, 30', 13)\n\t\t});\n\t}\n\n\tthis.objectType = vg.TILE;\n\tthis.entity = null;\n\tthis.userData = {};\n\n\tthis.selected = false;\n\tthis.highlight = '0x0084cc';\n\n\tthis.mesh = new THREE.Mesh(this.geometry, this.material);\n\tthis.mesh.userData.structure = this;\n\n\t// create references so we can control orientation through this (Tile), instead of drilling down\n\tthis.position = this.mesh.position;\n\tthis.rotation = this.mesh.rotation;\n\n\t// rotate it to face \"up\" (the threejs coordinate space is Y+)\n\tthis.rotation.x = -90 * vg.DEG_TO_RAD;\n\tthis.mesh.scale.set(settings.scale, settings.scale, 1);\n\n\tif (this.material.emissive) {\n\t\tthis._emissive = this.material.emissive.getHex();\n\t}\n\telse {\n\t\tthis._emissive = null;\n\t}\n};\n\nvg.Tile.prototype = {\n\tselect: function() {\n\t\tif (this.material.emissive) {\n\t\t\tthis.material.emissive.setHex(this.highlight);\n\t\t}\n\t\tthis.selected = true;\n\t\treturn this;\n\t},\n\n\tdeselect: function() {\n\t\tif (this._emissive !== null && this.material.emissive) {\n\t\t\tthis.material.emissive.setHex(this._emissive);\n\t\t}\n\t\tthis.selected = false;\n\t\treturn this;\n\t},\n\n\ttoggle: function() {\n\t\tif (this.selected) {\n\t\t\tthis.deselect();\n\t\t}\n\t\telse {\n\t\t\tthis.select();\n\t\t}\n\t\treturn this;\n\t},\n\n\tdispose: function() {\n\t\tif (this.cell && this.cell.tile) this.cell.tile = null;\n\t\tthis.cell = null;\n\t\tthis.position = null;\n\t\tthis.rotation = null;\n\t\tif (this.mesh.parent) this.mesh.parent.remove(this.mesh);\n\t\tthis.mesh.userData.structure = null;\n\t\tthis.mesh = null;\n\t\tthis.material = null;\n\t\tthis.userData = null;\n\t\tthis.entity = null;\n\t\tthis.geometry = null;\n\t\tthis._emissive = null;\n\t}\n};\n\nvg.Tile.prototype.constructor = vg.Tile;\n","/*\n\tA high-speed doubly-linked list of objects. Note that for speed reasons (using a dictionary lookup of\n\tcached nodes) there can only be a single instance of an object in the list at the same time. Adding the same\n\tobject a second time will result in a silent return from the add method.\n\n\tIn order to keep a track of node links, an object must be able to identify itself with a uniqueID function.\n\n\tTo add an item use:\n\t<pre><code>\n\t\tlist.add(newItem);\n\t</code></pre>\n\t<p>\n\tYou can iterate using the first and next members, such as:\n\t<pre><code>\n\t\tvar node = list.first;\n\t\twhile (node)\n\t\t{\n\t\t\tnode.object().DOSOMETHING();\n\t\t\tnode = node.next();\n\t\t}\n\t</code></pre>\n */\n(function() {\n\tvar LinkedListNode = function() {\n\t\tthis.obj = null;\n\t\tthis.next = null;\n\t\tthis.prev = null;\n\t\tthis.free = true;\n\t};\n\n\tvar LinkedList = function() {\n\t\tthis.first = null;\n\t\tthis.last = null;\n\t\tthis.length = 0;\n\t\tthis.objToNodeMap = {}; // a quick lookup list to map linked list nodes to objects\n\t\tthis.uniqueID = Date.now() + '' + Math.floor(Math.random()*1000);\n\n\t\tthis.sortArray = [];\n\t};\n\n\t// static function for utility\n\tLinkedList.generateID = function() {\n\t\treturn Math.random().toString(36).slice(2) + Date.now();\n\t};\n\n\tLinkedList.prototype = {\n\t\t/*\n\t\t\tGet the LinkedListNode for this object.\n\t\t\t@param obj The object to get the node for\n\t\t */\n\t\tgetNode: function(obj) {\n\t\t\t// objects added to a list must implement a uniqueID which returns a unique object identifier string\n\t\t\treturn this.objToNodeMap[obj.uniqueID];\n\t\t},\n\n\t\t/*\n\t\t\tAdds a new node to the list -- typically only used internally unless you're doing something funky\n\t\t\tUse add() to add an object to the list, not this.\n\t\t */\n\t\taddNode: function(obj) {\n\t\t\tvar node = new LinkedListNode();\n\t\t\tif (!obj.uniqueID) {\n\t\t\t\ttry {\n\t\t\t\t\tobj.uniqueID = LinkedList.generateID();\n\t\t\t\t\t// console.log('New ID: '+obj.uniqueID);\n\t\t\t\t}\n\t\t\t\tcatch (err) {\n\t\t\t\t\tconsole.error('[LinkedList.addNode] obj passed is immutable: cannot attach necessary identifier');\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tnode.obj = obj;\n\t\t\tnode.free = false;\n\t\t\tthis.objToNodeMap[obj.uniqueID] = node;\n\t\t\treturn node;\n\t\t},\n\n\t\tswapObjects: function(node, newObj) {\n\t\t\tthis.objToNodeMap[node.obj.uniqueID] = null;\n\t\t\tthis.objToNodeMap[newObj.uniqueID] = node;\n\t\t\tnode.obj = newObj;\n\t\t},\n\n\t\t/*\n\t\t\tAdd an item to the list\n\t\t\t@param obj The object to add\n\t\t */\n\t\tadd: function(obj) {\n\t\t\tvar node = this.objToNodeMap[obj.uniqueID];\n\n\t\t\tif (!node) {\n\t\t\t\tnode = this.addNode(obj);\n\t\t\t}\n\t\t\telse {\n\t\t\t\tif (node.free === false) return;\n\n\t\t\t\t// reusing a node, so we clean it up\n\t\t\t\t// this caching of node/object pairs is the reason an object can only exist\n\t\t\t\t// once in a list -- which also makes things faster (not always creating new node\n\t\t\t\t// object every time objects are moving on and off the list\n\t\t\t\tnode.obj = obj;\n\t\t\t\tnode.free = false;\n\t\t\t\tnode.next = null;\n\t\t\t\tnode.prev = null;\n\t\t\t}\n\n\t\t\t// append this obj to the end of the list\n\t\t\tif (!this.first) { // is this the first?\n\t\t\t\tthis.first = node;\n\t\t\t\tthis.last = node;\n\t\t\t\tnode.next = null; // clear just in case\n\t\t\t\tnode.prev = null;\n\t\t\t}\n\t\t\telse {\n\t\t\t\tif (!this.last) {\n\t\t\t\t\tthrow new Error(\"[LinkedList.add] No last in the list -- that shouldn't happen here\");\n\t\t\t\t}\n\n\t\t\t\t// add this entry to the end of the list\n\t\t\t\tthis.last.next = node; // current end of list points to the new end\n\t\t\t\tnode.prev = this.last;\n\t\t\t\tthis.last = node; // new object to add becomes last in the list\n\t\t\t\tnode.next = null; // just in case this was previously set\n\t\t\t}\n\t\t\tthis.length++;\n\n\t\t\tif (this.showDebug) this.dump('after add');\n\t\t},\n\n\t\thas: function(obj) {\n\t\t\treturn !!this.objToNodeMap[obj.uniqueID];\n\t\t},\n\n\t\t/*\n\t\t\tMoves this item upwards in the list\n\t\t\t@param obj\n\t\t */\n\t\tmoveUp: function(obj) {\n\t\t\tthis.dump('before move up');\n\t\t\tvar c = this.getNode(obj);\n\t\t\tif (!c) throw \"Oops, trying to move an object that isn't in the list\";\n\t\t\tif (!c.prev) return; // already first, ignore\n\n\t\t\t// This operation makes C swap places with B:\n\t\t\t// A <-> B <-> C <-> D\n\t\t\t// A <-> C <-> B <-> D\n\n\t\t\tvar b = c.prev;\n\t\t\tvar a = b.prev;\n\n\t\t\t// fix last\n\t\t\tif (c == this.last) this.last = b;\n\n\t\t\tvar oldCNext = c.next;\n\n\t\t\tif (a) a.next = c;\n\t\t\tc.next = b;\n\t\t\tc.prev = b.prev;\n\n\t\t\tb.next = oldCNext;\n\t\t\tb.prev = c;\n\n\t\t\t// check to see if we are now first\n\t\t\tif (this.first == b) this.first = c;\n\t\t},\n\n\t\t/*\n\t\t\tMoves this item downwards in the list\n\t\t\t@param obj\n\t\t */\n\t\tmoveDown: function(obj) {\n\t\t\tvar b = this.getNode(obj);\n\t\t\tif (!b) throw \"Oops, trying to move an object that isn't in the list\";\n\t\t\tif (!b.next) return; // already last, ignore\n\n\t\t\t// This operation makes B swap places with C:\n\t\t\t// A <-> B <-> C <-> D\n\t\t\t// A <-> C <-> B <-> D\n\n\t\t\tvar c = b.next;\n\t\t\tthis.moveUp(c.obj);\n\n\t\t\t// check to see if we are now last\n\t\t\tif (this.last == c) this.last = b;\n\t\t},\n\n\t\t/*\n\t\t\tTake everything off the list and put it in an array, sort it, then put it back.\n\t\t */\n\t\tsort: function(compare) {\n\t\t\tvar sortArray = this.sortArray;\n\t\t\tvar i, l, node = this.first;\n\t\t\tsortArray.length = 0;\n\n\t\t\twhile (node) {\n\t\t\t\tsortArray.push(node.obj);\n\t\t\t\tnode = node.next;\n\t\t\t}\n\n\t\t\tthis.clear();\n\n\t\t\tsortArray.sort(compare);\n\t\t\t// console.log(sortArray);\n\t\t\tl = sortArray.length;\n\t\t\tfor (i = 0; i < l; i++) {\n\t\t\t\tthis.add(sortArray[i]);\n\t\t\t}\n\t\t},\n\n\t\t/*\n\t\t\tRemoves an item from the list\n\t\t\t@param obj The object to remove\n\t\t\t@returns boolean true if the item was removed, false if the item was not on the list\n\t\t */\n\t\tremove: function(obj) {\n\t\t\tvar node = this.getNode(obj);\n\t\t\tif (!node || node.free){\n\t\t\t\treturn false; // ignore this error (trying to remove something not there)\n\t\t\t}\n\n\t\t\t// pull this object out and tie up the ends\n\t\t\tif (node.prev) node.prev.next = node.next;\n\t\t\tif (node.next) node.next.prev = node.prev;\n\n\t\t\t// fix first and last\n\t\t\tif (!node.prev) // if this was first on the list\n\t\t\t\tthis.first = node.next; // make the next on the list first (can be null)\n\t\t\tif (!node.next) // if this was the last\n\t\t\t\tthis.last = node.prev; // then this node's previous becomes last\n\n\t\t\tnode.free = true;\n\t\t\tnode.prev = null;\n\t\t\tnode.next = null;\n\n\t\t\tthis.length--;\n\n\t\t\treturn true;\n\t\t},\n\n\t\t// remove the head and return it's object\n\t\tshift: function() {\n\t\t\tvar node = this.first;\n\t\t\tif (this.length === 0) return null;\n\t\t\t// if (node == null || node.free == true) return null;\n\n\t\t\t// pull this object out and tie up the ends\n\t\t\tif (node.prev) {\n\t\t\t\tnode.prev.next = node.next;\n\t\t\t}\n\t\t\tif (node.next) {\n\t\t\t\tnode.next.prev = node.prev;\n\t\t\t}\n\n\t\t\t// make the next on the list first (can be null)\n\t\t\tthis.first = node.next;\n\t\t\tif (!node.next) this.last = null; // make sure we clear this\n\n\t\t\tnode.free = true;\n\t\t\tnode.prev = null;\n\t\t\tnode.next = null;\n\n\t\t\tthis.length--;\n\t\t\treturn node.obj;\n\t\t},\n\n\t\t// remove the tail and return it's object\n\t\tpop: function() {\n\t\t\tvar node = this.last;\n\t\t\tif (this.length === 0) return null;\n\n\t\t\t// pull this object out and tie up the ends\n\t\t\tif (node.prev) {\n\t\t\t\tnode.prev.next = node.next;\n\t\t\t}\n\t\t\tif (node.next) {\n\t\t\t\tnode.next.prev = node.prev;\n\t\t\t}\n\n\t\t\t// this node's previous becomes last\n\t\t\tthis.last = node.prev;\n\t\t\tif (!node.prev) this.first = null; // make sure we clear this\n\n\t\t\tnode.free = true;\n\t\t\tnode.prev = null;\n\t\t\tnode.next = null;\n\n\t\t\tthis.length--;\n\t\t\treturn node.obj;\n\t\t},\n\n\t\t/**\n\t\t * Add the passed list to this list, leaving it untouched.\n\t\t */\n\t\tconcat: function(list) {\n\t\t\tvar node = list.first;\n\t\t\twhile (node) {\n\t\t\t\tthis.add(node.obj);\n\t\t\t\tnode = node.next;\n\t\t\t}\n\t\t},\n\n\t\t/**\n\t\t * Clears the list out\n\t\t */\n\t\tclear: function() {\n\t\t\tvar next = this.first;\n\n\t\t\twhile (next) {\n\t\t\t\tnext.free = true;\n\t\t\t\tnext = next.next;\n\t\t\t}\n\n\t\t\tthis.first = null;\n\t\t\tthis.length = 0;\n\t\t},\n\n\t\tdispose: function() {\n\t\t\tvar next = this.first;\n\n\t\t\twhile (next) {\n\t\t\t\tnext.obj = null;\n\t\t\t\tnext = next.next;\n\t\t\t}\n\t\t\tthis.first = null;\n\n\t\t\tthis.objToNodeMap = null;\n\t\t},\n\n\t\t/*\n\t\t\tOutputs the contents of the current list for debugging.\n\t\t */\n\t\tdump: function(msg) {\n\t\t\tconsole.log('====================' + msg + '=====================');\n\t\t\tvar a = this.first;\n\t\t\twhile (a) {\n\t\t\t\tconsole.log(\"{\" + a.obj.toString() + \"} previous=\" + (a.prev ? a.prev.obj : \"NULL\"));\n\t\t\t\ta = a.next();\n\t\t\t}\n\t\t\tconsole.log(\"===================================\");\n\t\t\tconsole.log(\"Last: {\" + (this.last ? this.last.obj : 'NULL') + \"} \" +\n\t\t\t\t\"First: {\" + (this.first ? this.first.obj : 'NULL') + \"}\");\n\t\t}\n\t};\n\n\tLinkedList.prototype.constructor = LinkedList;\n\n\tvg.LinkedList = LinkedList;\n}());","(function() {\n var SignalBinding = function (signal, listener, isOnce, listenerContext, priority) {\n /**\n * @property _listener - Handler function bound to the signal.\n * @private\n */\n this._listener = listener;\n\n /**\n * @property {boolean} isOnce - If binding should be executed just once.\n * @private\n */\n this.isOnce = isOnce;\n\n /**\n * @property {object|undefined|null} context - Context on which listener will be executed (object that should represent the `this` variable inside listener function).\n */\n this.context = listenerContext;\n\n /**\n * @property {Signal} signal - Reference to Signal object that listener is currently bound to.\n * @private\n */\n this.signal = signal;\n\n /**\n * @property {number} _priority - Listener priority.\n * @private\n */\n this._priority = priority || 0;\n };\n\n SignalBinding.prototype = {\n /**\n * If binding is active and should be executed.\n * @property {boolean} active\n * @default\n */\n active: true,\n\n /**\n * Default parameters passed to listener during `Signal.dispatch` and `SignalBinding.execute` (curried parameters).\n * @property {array|null} params\n * @default\n */\n params: null,\n\n /**\n * Call listener passing arbitrary parameters.\n * If binding was added using `Signal.addOnce()` it will be automatically removed from signal dispatch queue, this method is used internally for the signal dispatch.\n * @method SignalBinding#execute\n * @param {array} [paramsArr] - Array of parameters that should be passed to the listener.\n * @return {any} Value returned by the listener.\n */\n execute: function(paramsArr) {\n\n var handlerReturn, params;\n\n if (this.active && !!this._listener) {\n params = this.params ? this.params.concat(paramsArr) : paramsArr;\n handlerReturn = this._listener.apply(this.context, params);\n\n if (this.isOnce) {\n this.detach();\n }\n }\n\n return handlerReturn;\n\n },\n\n /**\n * Detach binding from signal.\n * alias to: @see mySignal.remove(myBinding.listener);\n * @method SignalBinding#detach\n * @return {function|null} Handler function bound to the signal or `null` if binding was previously detached.\n */\n detach: function () {\n return this.isBound() ? this.signal.remove(this._listener, this.context) : null;\n },\n\n /**\n * @method SignalBinding#isBound\n * @return {boolean} True if binding is still bound to the signal and has a listener.\n */\n isBound: function () {\n return (!!this.signal && !!this._listener);\n },\n\n /**\n * Delete instance properties\n * @method SignalBinding#_destroy\n * @private\n */\n _destroy: function () {\n delete this.signal;\n delete this._listener;\n delete this.context;\n },\n\n /**\n * @method SignalBinding#toString\n * @return {string} String representation of the object.\n */\n toString: function () {\n return '[SignalBinding isOnce:' + this.isOnce +', isBound:'+ this.isBound() +', active:' + this.active + ']';\n }\n };\n\n SignalBinding.prototype.constructor = SignalBinding;\n\n\n\n /**\n * @author Miller Medeiros http://millermedeiros.github.com/js-signals/\n * @author Richard Davey <[email protected]>\n * @copyright 2014 Photon Storm Ltd.\n * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}\n */\n\n /**\n * A Signal is used for object communication via a custom broadcaster instead of Events.\n *\n * @class Signal\n * @constructor\n */\n var Signal = function () {\n /**\n * @property {Array.<SignalBinding>} _bindings - Internal variable.\n * @private\n */\n this._bindings = [];\n\n /**\n * @property {any} _prevParams - Internal variable.\n * @private\n */\n this._prevParams = null;\n\n // enforce dispatch to aways work on same context (#47)\n var self = this;\n\n /**\n * @property {function} dispatch - The dispatch function is what sends the Signal out.\n */\n this.dispatch = function(){\n Signal.prototype.dispatch.apply(self, arguments);\n };\n\n };\n\n Signal.prototype = {\n /**\n * If Signal should keep record of previously dispatched parameters and\n * automatically execute listener during `add()`/`addOnce()` if Signal was\n * already dispatched before.\n * @property {boolean} memorize\n */\n memorize: false,\n\n /**\n * @property {boolean} _shouldPropagate\n * @private\n */\n _shouldPropagate: true,\n\n /**\n * If Signal is active and should broadcast events.\n * IMPORTANT: Setting this property during a dispatch will only affect the next dispatch, if you want to stop the propagation of a signal use `halt()` instead.\n * @property {boolean} active\n * @default\n */\n active: true,\n\n /**\n * @method Signal#validateListener\n * @param {function} listener - Signal handler function.\n * @param {string} fnName - Function name.\n * @private\n */\n validateListener: function (listener, fnName) {\n if (typeof listener !== 'function') {\n throw new Error('Signal: listener is a required param of {fn}() and should be a Function.'.replace('{fn}', fnName));\n }\n },\n\n /**\n * @method Signal#_registerListener\n * @private\n * @param {function} listener - Signal handler function.\n * @param {boolean} isOnce - Should the listener only be called once?\n * @param {object} [listenerContext] - The context under which the listener is invoked.\n * @param {number} [priority] - The priority level of the event listener. Listeners with higher priority will be executed before listeners with lower priority. Listeners with same priority level will be executed at the same order as they were added. (default = 0).\n * @return {SignalBinding} An Object representing the binding between the Signal and listener.\n */\n _registerListener: function (listener, isOnce, listenerContext, priority) {\n var prevIndex = this._indexOfListener(listener, listenerContext);\n var binding;\n\n if (prevIndex !== -1) {\n binding = this._bindings[prevIndex];\n\n if (binding.isOnce !== isOnce) {\n throw new Error('You cannot add' + (isOnce ? '' : 'Once') + '() then add' + (!isOnce ? '' : 'Once') + '() the same listener without removing the relationship first.');\n }\n }\n else {\n binding = new SignalBinding(this, listener, isOnce, listenerContext, priority);\n this._addBinding(binding);\n }\n\n if (this.memorize && this._prevParams) {\n binding.execute(this._prevParams);\n }\n\n return binding;\n },\n\n /**\n * @method Signal#_addBinding\n * @private\n * @param {SignalBinding} binding - An Object representing the binding between the Signal and listener.\n */\n _addBinding: function (binding) {\n // Simplified insertion sort\n var n = this._bindings.length;\n\n do {\n n--;\n }\n while (this._bindings[n] && binding._priority <= this._bindings[n]._priority);\n\n this._bindings.splice(n + 1, 0, binding);\n },\n\n /**\n * @method Signal#_indexOfListener\n * @private\n * @param {function} listener - Signal handler function.\n * @return {number} The index of the listener within the private bindings array.\n */\n _indexOfListener: function (listener, context) {\n var n = this._bindings.length;\n var cur;\n\n while (n--) {\n cur = this._bindings[n];\n\n if (cur._listener === listener && cur.context === context) {\n return n;\n }\n }\n\n return -1;\n },\n\n /**\n * Check if listener was attached to Signal.\n *\n * @method Signal#has\n * @param {function} listener - Signal handler function.\n * @param {object} [context] - Context on which listener will be executed (object that should represent the `this` variable inside listener function).\n * @return {boolean} If Signal has the specified listener.\n */\n has: function (listener, context) {\n return this._indexOfListener(listener, context) !== -1;\n },\n\n /**\n * Add a listener to the signal.\n *\n * @method Signal#add\n * @param {function} listener - The function to call when this Signal is dispatched.\n * @param {object} [listenerContext] - The context under which the listener will be executed (i.e. the object that should represent the `this` variable).\n * @param {number} [priority] - The priority level of the event listener. Listeners with higher priority will be executed before listeners with lower priority. Listeners with same priority level will be executed at the same order as they were added (default = 0)\n * @return {SignalBinding} An Object representing the binding between the Signal and listener.\n */\n add: function (listener, listenerContext, priority) {\n this.validateListener(listener, 'add');\n\n return this._registerListener(listener, false, listenerContext, priority);\n },\n\n /**\n * Add listener to the signal that should be removed after first execution (will be executed only once).\n *\n * @method Signal#addOnce\n * @param {function} listener - The function to call when this Signal is dispatched.\n * @param {object} [listenerContext] - The context under which the listener will be executed (i.e. the object that should represent the `this` variable).\n * @param {number} [priority] - The priority level of the event listener. Listeners with higher priority will be executed before listeners with lower priority. Listeners with same priority level will be executed at the same order as they were added (default = 0)\n * @return {SignalBinding} An Object representing the binding between the Signal and listener.\n */\n addOnce: function (listener, listenerContext, priority) {\n this.validateListener(listener, 'addOnce');\n\n return this._registerListener(listener, true, listenerContext, priority);\n },\n\n /**\n * Remove a single listener from the dispatch queue.\n *\n * @method Signal#remove\n * @param {function} listener - Handler function that should be removed.\n * @param {object} [context] - Execution context (since you can add the same handler multiple times if executing in a different context).\n * @return {function} Listener handler function.\n */\n remove: function (listener, context) {\n this.validateListener(listener, 'remove');\n\n var i = this._indexOfListener(listener, context);\n\n if (i !== -1) {\n this._bindings[i]._destroy(); //no reason to a SignalBinding exist if it isn't attached to a signal\n this._bindings.splice(i, 1);\n }\n\n return listener;\n },\n\n /**\n * Remove all listeners from the Signal.\n *\n * @method Signal#removeAll\n * @param {object} [context=null] - If specified only listeners for the given context will be removed.\n */\n removeAll: function (context) {\n if (typeof context === 'undefined') { context = null; }\n\n var n = this._bindings.length;\n\n while (n--) {\n if (context) {\n if (this._bindings[n].context === context) {\n this._bindings[n]._destroy();\n this._bindings.splice(n, 1);\n }\n }\n else {\n this._bindings[n]._destroy();\n }\n }\n\n if (!context) {\n this._bindings.length = 0;\n }\n },\n\n /**\n * Gets the total number of listeneres attached to ths Signal.\n *\n * @method Signal#getNumListeners\n * @return {number} Number of listeners attached to the Signal.\n */\n getNumListeners: function () {\n return this._bindings.length;\n },\n\n /**\n * Stop propagation of the event, blocking the dispatch to next listeners on the queue.\n * IMPORTANT: should be called only during signal dispatch, calling it before/after dispatch won't affect signal broadcast.\n * @see Signal.prototype.disable\n *\n * @method Signal#halt\n */\n halt: function () {\n this._shouldPropagate = false;\n },\n\n /**\n * Dispatch/Broadcast Signal to all listeners added to the queue.\n *\n * @method Signal#dispatch\n * @param {any} [params] - Parameters that should be passed to each handler.\n */\n dispatch: function () {\n if (!this.active) {\n return;\n }\n\n var paramsArr = Array.prototype.slice.call(arguments);\n var n = this._bindings.length;\n var bindings;\n\n if (this.memorize) {\n this._prevParams = paramsArr;\n }\n\n if (!n) {\n // Should come after memorize\n return;\n }\n\n bindings = this._bindings.slice(); //clone array in case add/remove items during dispatch\n this._shouldPropagate = true; //in case `halt` was called before dispatch or during the previous dispatch.\n\n //execute all callbacks until end of the list or until a callback returns `false` or stops propagation\n //reverse loop since listeners with higher priority will be added at the end of the list\n do {\n n--;\n }\n while (bindings[n] && this._shouldPropagate && bindings[n].execute(paramsArr) !== false);\n },\n\n /**\n * Forget memorized arguments.\n * @see Signal.memorize\n *\n * @method Signal#forget\n */\n forget: function() {\n this._prevParams = null;\n },\n\n /**\n * Remove all bindings from signal and destroy any reference to external objects (destroy Signal object).\n * IMPORTANT: calling any method on the signal instance after calling dispose will throw errors.\n *\n * @method Signal#dispose\n */\n dispose: function () {\n this.removeAll();\n\n delete this._bindings;\n delete this._prevParams;\n },\n\n /**\n *\n * @method Signal#toString\n * @return {string} String representation of the object.\n */\n toString: function () {\n return '[Signal active:'+ this.active +' numListeners:'+ this.getNumListeners() +']';\n }\n\n };\n\n Signal.prototype.constructor = Signal;\n\n vg.Signal = Signal;\n}());\n","/*\n\tA* path-finder based upon http://www.redblobgames.com/pathfinding/a-star/introduction.html\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n */\n// 'utils/Tools', 'lib/LinkedList'\nvg.AStarFinder = function(finderConfig) {\n\tfinderConfig = finderConfig || {};\n\n\tvar settings = {\n\t\tallowDiagonal: false,\n\t\theuristicFilter: null\n\t};\n\tsettings = vg.Tools.merge(settings, finderConfig);\n\n\tthis.allowDiagonal = settings.allowDiagonal;\n\tthis.heuristicFilter = settings.heuristicFilter;\n\n\tthis.list = new vg.LinkedList();\n};\n\nvg.AStarFinder.prototype = {\n\t/*\n\t\tFind and return the path.\n\t\t@return Array<Cell> The path, including both start and end positions. Null if it failed.\n\t */\n\tfindPath: function(startNode, endNode, heuristic, grid) {\n\t\tvar current, costSoFar, neighbors, n, i, l;\n\t\theuristic = heuristic || this.heuristicFilter;\n\t\t// clear old values from previous finding\n\t\tgrid.clearPath();\n\t\tthis.list.clear();\n\n\t\t// push the start current into the open list\n\t\tthis.list.add(startNode);\n\n\t\t// while the open list is not empty\n\t\twhile (this.list.length > 0) {\n\t\t\t// sort so lowest cost is first\n\t\t\tthis.list.sort(this.compare);\n\n\t\t\t// pop the position of current which has the minimum `_calcCost` value.\n\t\t\tcurrent = this.list.shift();\n\t\t\tcurrent._visited = true;\n\n\t\t\t// if reached the end position, construct the path and return it\n\t\t\tif (current === endNode) {\n\t\t\t\treturn vg.PathUtil.backtrace(endNode);\n\t\t\t}\n\n\t\t\t// cycle through each neighbor of the current current\n\t\t\tneighbors = grid.getNeighbors(current, this.allowDiagonal, heuristic);\n\t\t\tfor (i = 0, l = neighbors.length; i < l; i++) {\n\t\t\t\tn = neighbors[i];\n\n\t\t\t\tif (!n.walkable) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tcostSoFar = current._calcCost + grid.distance(current, n);\n\n\t\t\t\t// check if the neighbor has not been inspected yet, or can be reached with smaller cost from the current node\n\t\t\t\tif (!n._visited || costSoFar < n._calcCost) {\n\t\t\t\t\tn._visited = true;\n\t\t\t\t\tn._parent = current;\n\t\t\t\t\tn._calcCost = costSoFar;\n\t\t\t\t\t// console.log(n);\n\t\t\t\t\t// _priority is the most important property, since it makes the algorithm \"greedy\" and seek the goal.\n\t\t\t\t\t// otherwise it behaves like a brushfire/breadth-first\n\t\t\t\t\tn._priority = costSoFar + grid.distance(endNode, n);\n\n\t\t\t\t\t// check neighbor if it's the end current as well--often cuts steps by a significant amount\n\t\t\t\t\tif (n === endNode) {\n\t\t\t\t\t\treturn vg.PathUtil.backtrace(endNode);\n\t\t\t\t\t}\n\t\t\t\t\t// console.log(n);\n\t\t\t\t\tthis.list.add(n);\n\t\t\t\t}\n\t\t\t\t// console.log(this.list);\n\t\t\t} // end for each neighbor\n\t\t} // end while not open list empty\n\t\t// failed to find the path\n\t\treturn null;\n\t},\n\n\tcompare: function(nodeA, nodeB) {\n\t\treturn nodeA._priority - nodeB._priority;\n\t}\n};\n\nvg.AStarFinder.prototype.constructor = vg.AStarFinder;","/*\n\t@source https://github.com/qiao/PathFinding.js/\n*/\nvg.PathUtil = {\n\t/**\n\t * Backtrace according to the parent records and return the path.\n\t * (including both start and end nodes)\n\t * @param {Node} node End node\n\t * @return {Array.<Array.<number>>} the path\n\t */\n\tbacktrace: function(node) {\n\t\tvar path = [node];\n\t\twhile (node._parent) {\n\t\t\tnode = node._parent;\n\t\t\tpath.push(node);\n\t\t}\n\t\treturn path.reverse();\n\t},\n\n\t/**\n\t * Backtrace from start and end node, and return the path.\n\t * (including both start and end nodes)\n\t * @param {Node}\n\t * @param {Node}\n\t */\n\tbiBacktrace: function(nodeA, nodeB) {\n\t\tvar pathA = this.backtrace(nodeA),\n\t\t\tpathB = this.backtrace(nodeB);\n\t\treturn pathA.concat(pathB.reverse());\n\t},\n\n\t/**\n\t * Compute the length of the path.\n\t * @param {Array.<Array.<number>>} path The path\n\t * @return {number} The length of the path\n\t */\n\tpathLength: function(path) {\n\t\tvar i, sum = 0, a, b, dx, dy;\n\t\tfor (i = 1; i < path.length; ++i) {\n\t\t\ta = path[i - 1];\n\t\t\tb = path[i];\n\t\t\tdx = a[0] - b[0];\n\t\t\tdy = a[1] - b[1];\n\t\t\tsum += Math.sqrt(dx * dx + dy * dy);\n\t\t}\n\t\treturn sum;\n\t},\n\n\n\t/**\n\t * Given the start and end coordinates, return all the coordinates lying\n\t * on the line formed by these coordinates, based on Bresenham's algorithm.\n\t * http://en.wikipedia.org/wiki/Bresenham's_line_algorithm#Simplification\n\t * @param {number} x0 Start x coordinate\n\t * @param {number} y0 Start y coordinate\n\t * @param {number} x1 End x coordinate\n\t * @param {number} y1 End y coordinate\n\t * @return {Array.<Array.<number>>} The coordinates on the line\n\t */\n\tinterpolate: function(x0, y0, x1, y1) {\n\t\tvar abs = Math.abs,\n\t\t\tline = [],\n\t\t\tsx, sy, dx, dy, err, e2;\n\n\t\tdx = abs(x1 - x0);\n\t\tdy = abs(y1 - y0);\n\n\t\tsx = (x0 < x1) ? 1 : -1;\n\t\tsy = (y0 < y1) ? 1 : -1;\n\n\t\terr = dx - dy;\n\n\t\twhile (x0 !== x1 || y0 !== y1) {\n\t\t\tline.push([x0, y0]);\n\n\t\t\te2 = 2 * err;\n\t\t\tif (e2 > -dy) {\n\t\t\t\terr = err - dy;\n\t\t\t\tx0 = x0 + sx;\n\t\t\t}\n\t\t\tif (e2 < dx) {\n\t\t\t\terr = err + dx;\n\t\t\t\ty0 = y0 + sy;\n\t\t\t}\n\t\t}\n\n\t\treturn line;\n\t},\n\n\n\t/**\n\t * Given a compressed path, return a new path that has all the segments\n\t * in it interpolated.\n\t * @param {Array.<Array.<number>>} path The path\n\t * @return {Array.<Array.<number>>} expanded path\n\t */\n\texpandPath: function(path) {\n\t\tvar expanded = [],\n\t\t\tlen = path.length,\n\t\t\tcoord0, coord1,\n\t\t\tinterpolated,\n\t\t\tinterpolatedLen,\n\t\t\ti, j;\n\n\t\tif (len < 2) {\n\t\t\treturn expanded;\n\t\t}\n\n\t\tfor (i = 0; i < len - 1; ++i) {\n\t\t\tcoord0 = path[i];\n\t\t\tcoord1 = path[i + 1];\n\n\t\t\tinterpolated = this.interpolate(coord0[0], coord0[1], coord1[0], coord1[1]);\n\t\t\tinterpolatedLen = interpolated.length;\n\t\t\tfor (j = 0; j < interpolatedLen - 1; ++j) {\n\t\t\t\texpanded.push(interpolated[j]);\n\t\t\t}\n\t\t}\n\t\texpanded.push(path[len - 1]);\n\n\t\treturn expanded;\n\t},\n\n\n\t/**\n\t * Smoothen the give path.\n\t * The original path will not be modified; a new path will be returned.\n\t * @param {PF.Grid} grid\n\t * @param {Array.<Array.<number>>} path The path\n\t */\n\tsmoothenPath: function(grid, path) {\n\t\tvar len = path.length,\n\t\t\tx0 = path[0][0], // path start x\n\t\t\ty0 = path[0][1], // path start y\n\t\t\tx1 = path[len - 1][0], // path end x\n\t\t\ty1 = path[len - 1][1], // path end y\n\t\t\tsx, sy, // current start coordinate\n\t\t\tex, ey, // current end coordinate\n\t\t\tnewPath,\n\t\t\tlastValidCoord,\n\t\t\ti, j, coord, line, testCoord, blocked;\n\n\t\tsx = x0;\n\t\tsy = y0;\n\t\tnewPath = [[sx, sy]];\n\n\t\tfor (i = 2; i < len; ++i) {\n\t\t\tcoord = path[i];\n\t\t\tex = coord[0];\n\t\t\tey = coord[1];\n\t\t\tline = this.interpolate(sx, sy, ex, ey);\n\n\t\t\tblocked = false;\n\t\t\tfor (j = 1; j < line.length; ++j) {\n\t\t\t\ttestCoord = line[j];\n\n\t\t\t\tif (!grid.isWalkableAt(testCoord[0], testCoord[1])) {\n\t\t\t\t\tblocked = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (blocked) {\n\t\t\t\tlastValidCoord = path[i - 1];\n\t\t\t\tnewPath.push(lastValidCoord);\n\t\t\t\tsx = lastValidCoord[0];\n\t\t\t\tsy = lastValidCoord[1];\n\t\t\t}\n\t\t}\n\t\tnewPath.push([x1, y1]);\n\n\t\treturn newPath;\n\t},\n\n\n\t/**\n\t * Compress a path, remove redundant nodes without altering the shape\n\t * The original path is not modified\n\t * @param {Array.<Array.<number>>} path The path\n\t * @return {Array.<Array.<number>>} The compressed path\n\t */\n\tcompressPath: function(path) {\n\n\t\t// nothing to compress\n\t\tif (path.length < 3) {\n\t\t\treturn path;\n\t\t}\n\n\t\tvar compressed = [],\n\t\t\tsx = path[0][0], // start x\n\t\t\tsy = path[0][1], // start y\n\t\t\tpx = path[1][0], // second point x\n\t\t\tpy = path[1][1], // second point y\n\t\t\tdx = px - sx, // direction between the two points\n\t\t\tdy = py - sy, // direction between the two points\n\t\t\tlx, ly,\n\t\t\tldx, ldy,\n\t\t\tsq, i;\n\n\t\t// normalize the direction\n\t\tsq = Math.sqrt(dx*dx + dy*dy);\n\t\tdx /= sq;\n\t\tdy /= sq;\n\n\t\t// start the new path\n\t\tcompressed.push([sx,sy]);\n\n\t\tfor (i = 2; i < path.length; i++) {\n\n\t\t\t// store the last point\n\t\t\tlx = px;\n\t\t\tly = py;\n\n\t\t\t// store the last direction\n\t\t\tldx = dx;\n\t\t\tldy = dy;\n\n\t\t\t// next point\n\t\t\tpx = path[i][0];\n\t\t\tpy = path[i][1];\n\n\t\t\t// next direction\n\t\t\tdx = px - lx;\n\t\t\tdy = py - ly;\n\n\t\t\t// normalize\n\t\t\tsq = Math.sqrt(dx*dx + dy*dy);\n\t\t\tdx /= sq;\n\t\t\tdy /= sq;\n\n\t\t\t// if the direction has changed, store the point\n\t\t\tif (dx !== ldx || dy !== ldy) {\n\t\t\t\tcompressed.push([lx,ly]);\n\t\t\t}\n\t\t}\n\n\t\t// store the last point\n\t\tcompressed.push([px,py]);\n\n\t\treturn compressed;\n\t}\n};\n","vg.Loader = {\n\tmanager: null,\n\timageLoader: null,\n\tcrossOrigin: false,\n\n\tinit: function(crossOrigin) {\n\t\tthis.crossOrigin = crossOrigin || false;\n\n\t\tthis.manager = new THREE.LoadingManager(function() {\n\t\t\t// called when all images are loaded, so call your state manager or something\n\t\t}, function() {\n\t\t\t// noop\n\t\t}, function() {\n\t\t\tconsole.warn('Error loading images');\n\t\t});\n\n\t\tthis.imageLoader = new THREE.ImageLoader(this.manager);\n\t\tthis.imageLoader.crossOrigin = crossOrigin;\n\t},\n\n\tloadTexture: function(url, mapping, onLoad, onError) {\n\t\tvar texture = new THREE.Texture(null, mapping);\n\t\tthis.imageLoader.load(url, function(image) { // on load\n\t\t\t\ttexture.image = image;\n\t\t\t\ttexture.needsUpdate = true;\n\t\t\t\tif (onLoad) onLoad(texture);\n\t\t\t},\n\t\t\tnull, // on progress\n\t\t\tfunction (evt) { // on error\n\t\t\t\tif (onError) onError(evt);\n\t\t\t});\n\t\ttexture.sourceFile = url;\n\n\t\treturn texture;\n\t}\n};\n","/*\n\tTranslates mouse interactivity into 3D positions, so we can easily pick objects in the scene.\n\n\tLike everything else in ThreeJS, ray casting creates a ton of new objects each time it's used. This contributes to frequent garbage collections (causing frame hitches), so if you're limited to low-end hardware like mobile, it would be better to only update it when the user clicks, instead of every frame (so no hover effects, but on mobile those don't work anyway). You'll want to create a version that handles touch anyway.\n\n\tgroup - any Object3D (Scene, Group, Mesh, Sprite, etc) that the mouse will cast against\n\tcamera - the camera to cast from\n\t[element] - optional element to attach mouse event to\n\n\t@author Corey Birnbaum https://github.com/vonWolfehaus/\n */\nvg.MouseCaster = function(group, camera, element) {\n\tthis.down = false; // left click\n\tthis.rightDown = false;\n\t// the object that was just clicked on\n\tthis.pickedObject = null;\n\t// the object currently being 'held'\n\tthis.selectedObject = null;\n\t// store the results of the last cast\n\tthis.allHits = null;\n\t// disable the caster easily to temporarily prevent user input\n\tthis.active = true;\n\n\tthis.shift = false;\n\tthis.ctrl = false;\n\tthis.wheel = 0;\n\n\t// you can track exactly where the mouse is in the 3D scene by using the z component\n\tthis.position = new THREE.Vector3();\n\tthis.screenPosition = new THREE.Vector2();\n\tthis.signal = new vg.Signal();\n\tthis.group = group;\n\n\t// behind-the-scenes stuff you shouldn't worry about\n\tthis._camera = camera;\n\tthis._raycaster = new THREE.Raycaster();\n\tthis._preventDefault = false;\n\n\telement = element || document;\n\n\telement.addEventListener('mousemove', this._onDocumentMouseMove.bind(this), false);\n\telement.addEventListener('mousedown', this._onDocumentMouseDown.bind(this), false);\n\telement.addEventListener('mouseup', this._onDocumentMouseUp.bind(this), false);\n\telement.addEventListener('mousewheel', this._onMouseWheel.bind(this), false);\n\telement.addEventListener('DOMMouseScroll', this._onMouseWheel.bind(this), false); // firefox\n};\n\n// statics to describe the events we dispatch\nvg.MouseCaster.OVER = 'over';\nvg.MouseCaster.OUT = 'out';\nvg.MouseCaster.DOWN = 'down';\nvg.MouseCaster.UP = 'up';\nvg.MouseCaster.CLICK = 'click'; // only fires if the user clicked down and up while on the same object\nvg.MouseCaster.WHEEL = 'wheel';\n\nvg.MouseCaster.prototype = {\n\tupdate: function() {\n\t\tif (!this.active) {\n\t\t\treturn;\n\t\t}\n\n\t\tthis._raycaster.setFromCamera(this.screenPosition, this._camera);\n\n\t\tvar intersects = this._raycaster.intersectObject(this.group, true);\n\t\tvar hit, obj;\n\n\t\tif (intersects.length > 0) {\n\t\t\t// get the first object under the mouse\n\t\t\thit = intersects[0];\n\t\t\tobj = hit.object.userData.structure;\n\t\t\tif (this.pickedObject != obj) {\n\t\t\t\t// the first object changed, meaning there's a different one, or none at all\n\t\t\t\tif (this.pickedObject) {\n\t\t\t\t\t// it's a new object, notify the old object is going away\n\t\t\t\t\tthis.signal.dispatch(vg.MouseCaster.OUT, this.pickedObject);\n\t\t\t\t}\n\t\t\t\t/*else {\n\t\t\t\t\t// hit a new object when nothing was there previously\n\t\t\t\t}*/\n\t\t\t\tthis.pickedObject = obj;\n\t\t\t\tthis.selectedObject = null; // cancel click, otherwise it'll confuse the user\n\n\t\t\t\tthis.signal.dispatch(vg.MouseCaster.OVER, this.pickedObject);\n\t\t\t}\n\t\t\tthis.position.copy(hit.point);\n\t\t\tthis.screenPosition.z = hit.distance;\n\t\t}\n\t\telse {\n\t\t\t// there isn't anything under the mouse\n\t\t\tif (this.pickedObject) {\n\t\t\t\t// there was though, we just moved out\n\t\t\t\tthis.signal.dispatch(vg.MouseCaster.OUT, this.pickedObject);\n\t\t\t}\n\t\t\tthis.pickedObject = null;\n\t\t\tthis.selectedObject = null;\n\t\t}\n\n\t\tthis.allHits = intersects;\n\t},\n\n\tpreventDefault: function() {\n\t\tthis._preventDefault = true;\n\t},\n\n\t_onDocumentMouseDown: function(evt) {\n\t\tevt = evt || window.event;\n\t\tevt.preventDefault();\n\t\tif (this._preventDefault) {\n\t\t\tthis._preventDefault = false;\n\t\t\treturn false;\n\t\t}\n\t\tif (this.pickedObject) {\n\t\t\tthis.selectedObject = this.pickedObject;\n\t\t}\n\t\tthis.shift = evt.shiftKey;\n\t\tthis.ctrl = evt.ctrlKey;\n\n\t\tthis.down = evt.which === 1;\n\t\tthis.rightDown = evt.which === 3;\n\n\t\tthis.signal.dispatch(vg.MouseCaster.DOWN, this.pickedObject);\n\t},\n\n\t_onDocumentMouseUp: function(evt) {\n\t\tevt.preventDefault();\n\t\tif (this._preventDefault) {\n\t\t\tthis._preventDefault = false;\n\t\t\treturn false;\n\t\t}\n\t\tthis.shift = evt.shiftKey;\n\t\tthis.ctrl = evt.ctrlKey;\n\n\t\tthis.signal.dispatch(vg.MouseCaster.UP, this.pickedObject);\n\t\tif (this.selectedObject && this.pickedObject && this.selectedObject.uniqueID === this.pickedObject.uniqueID) {\n\t\t\tthis.signal.dispatch(vg.MouseCaster.CLICK, this.pickedObject);\n\t\t}\n\n\t\tthis.down = evt.which === 1 ? false : this.down;\n\t\tthis.rightDown = evt.which === 3 ? false : this.rightDown;\n\t},\n\n\t_onDocumentMouseMove: function(evt) {\n\t\tevt.preventDefault();\n\t\tthis.screenPosition.x = (evt.clientX / window.innerWidth) * 2 - 1;\n\t\tthis.screenPosition.y = -(evt.clientY / window.innerHeight) * 2 + 1;\n\t},\n\n\t_onMouseWheel: function(evt) {\n\t\tif (!this.active) {\n\t\t\treturn;\n\t\t}\n\t\tevt.preventDefault();\n\t\tevt.stopPropagation();\n\n\t\tvar delta = 0;\n\t\tif (evt.wheelDelta !== undefined) { // WebKit / Opera / Explorer 9\n\t\t\tdelta = evt.wheelDelta;\n\t\t}\n\t\telse if (evt.detail !== undefined) { // Firefox\n\t\t\tdelta = -evt.detail;\n\t\t}\n\t\tif (delta > 0) {\n\t\t\tthis.wheel++;\n\t\t}\n\t\telse {\n\t\t\tthis.wheel--;\n\t\t}\n\t\t// console.log(this.wheel);\n\t\tthis.signal.dispatch(vg.MouseCaster.WHEEL, this.wheel);\n\t}\n};\n\nvg.MouseCaster.prototype.constructor = vg.MouseCaster;\n","/*\n\tSets up and manages a THREEjs container, camera, and light, making it easy to get going.\n\tAlso provides camera control.\n\n\tAssumes full screen.\n */\n// 'utils/Tools'\nvg.Scene = function(sceneConfig, controlConfig) {\n\tvar sceneSettings = {\n\t\telement: document.body,\n\t\talpha: true,\n\t\tantialias: true,\n\t\tclearColor: '#fff',\n\t\tsortObjects: false,\n\t\tfog: null,\n\t\tlight: new THREE.DirectionalLight(0xffffff),\n\t\tlightPosition: null,\n\t\tcameraType: 'PerspectiveCamera',\n\t\tcameraPosition: null, // {x, y, z}\n\t\torthoZoom: 4\n\t};\n\n\tvar controlSettings = {\n\t\tminDistance: 100,\n\t\tmaxDistance: 1000,\n\t\tzoomSpeed: 2,\n\t\tnoZoom: false\n\t};\n\n\tsceneSettings = vg.Tools.merge(sceneSettings, sceneConfig);\n\tif (typeof controlConfig !== 'boolean') {\n\t\tcontrolSettings = vg.Tools.merge(controlSettings, controlConfig);\n\t}\n\n\tthis.renderer = new THREE.WebGLRenderer({\n\t\talpha: sceneSettings.alpha,\n\t\tantialias: sceneSettings.antialias\n\t});\n\tthis.renderer.setClearColor(sceneSettings.clearColor, 0);\n\tthis.renderer.sortObjects = sceneSettings.sortObjects;\n\n\tthis.width = window.innerWidth;\n\tthis.height = window.innerHeight;\n\n\tthis.orthoZoom = sceneSettings.orthoZoom;\n\n\tthis.container = new THREE.Scene();\n\tthis.container.fog = sceneSettings.fog;\n\n\tthis.container.add(new THREE.AmbientLight(0xdddddd));\n\n\tif (!sceneSettings.lightPosition) {\n\t\tsceneSettings.light.position.set(-1, 1, -1).normalize();\n\t}\n\tthis.container.add(sceneSettings.light);\n\n\tif (sceneSettings.cameraType === 'OrthographicCamera') {\n\t\tvar width = window.innerWidth / this.orthoZoom;\n\t\tvar height = window.innerHeight / this.orthoZoom;\n\t\tthis.camera = new THREE.OrthographicCamera(width / -2, width / 2, height / 2, height / -2, 1, 5000);\n\t}\n\telse {\n\t\tthis.camera = new THREE.PerspectiveCamera(50, this.width / this.height, 1, 5000);\n\t}\n\n\tthis.contolled = !!controlConfig;\n\tif (this.contolled) {\n\t\tthis.controls = new THREE.OrbitControls(this.camera, this.renderer.domElement);\n\t\tthis.controls.minDistance = controlSettings.minDistance;\n\t\tthis.controls.maxDistance = controlSettings.maxDistance;\n\t\tthis.controls.zoomSpeed = controlSettings.zoomSpeed;\n\t\tthis.controls.noZoom = controlSettings.noZoom;\n\t}\n\n\tif (sceneSettings.cameraPosition) {\n\t\tthis.camera.position.copy(sceneSettings.cameraPosition);\n\t}\n\n\twindow.addEventListener('resize', function onWindowResize() {\n\t\tthis.width = window.innerWidth;\n\t\tthis.height = window.innerHeight;\n\t\tif (this.camera.type === 'OrthographicCamera') {\n\t\t\tvar width = this.width / this.orthoZoom;\n\t\t\tvar height = this.height / this.orthoZoom;\n\t\t\tthis.camera.left = width / -2;\n\t\t\tthis.camera.right = width / 2;\n\t\t\tthis.camera.top = height / 2;\n\t\t\tthis.camera.bottom = height / -2;\n\t\t}\n\t\telse {\n\t\t\tthis.camera.aspect = this.width / this.height;\n\t\t}\n\t\tthis.camera.updateProjectionMatrix();\n\t\tthis.renderer.setSize(this.width, this.height);\n\t}.bind(this), false);\n\n\tthis.attachTo(sceneSettings.element);\n};\n\nvg.Scene.prototype = {\n\n\tattachTo: function(element) {\n\t\telement.style.width = this.width + 'px';\n\t\telement.style.height = this.height + 'px';\n\t\tthis.renderer.setPixelRatio(window.devicePixelRatio);\n\t\tthis.renderer.setSize(this.width, this.height);\n\t\telement.appendChild(this.renderer.domElement);\n\t},\n\n\tadd: function(mesh) {\n\t\tthis.container.add(mesh);\n\t},\n\n\tremove: function(mesh) {\n\t\tthis.container.remove(mesh);\n\t},\n\n\trender: function() {\n\t\tif (this.contolled) this.controls.update();\n\t\tthis.renderer.render(this.container, this.camera);\n\t},\n\n\tupdateOrthoZoom: function() {\n\t\tif (this.orthoZoom <= 0) {\n\t\t\tthis.orthoZoom = 0;\n\t\t\treturn;\n\t\t}\n\t\tvar width = this.width / this.orthoZoom;\n\t\tvar height = this.height / this.orthoZoom;\n\t\tthis.camera.left = width / -2;\n\t\tthis.camera.right = width / 2;\n\t\tthis.camera.top = height / 2;\n\t\tthis.camera.bottom = height / -2;\n\t\tthis.camera.updateProjectionMatrix();\n\t},\n\n\tfocusOn: function(obj) {\n\t\tthis.camera.lookAt(obj.position);\n\t}\n};\n\nvg.Scene.prototype.constructor = vg.Scene;\n","// 'utils/Tools', 'lib/LinkedList', 'utils/MouseCaster', 'lib/Signal'\nvg.SelectionManager = function(mouse) {\n\tthis.mouse = mouse;\n\n\tthis.onSelect = new vg.Signal();\n\tthis.onDeselect = new vg.Signal();\n\n\tthis.selected = null;\n\t// deselect if player clicked on the same thing twice\n\tthis.toggleSelection = false;\n\n\t// allow multiple entities to be selected at once\n\t// this.multiselect = false; // todo\n\t// this.allSelected = new LinkedList();\n\n\tthis.mouse.signal.add(this.onMouse, this);\n}\n\nvg.SelectionManager.prototype = {\n\tselect: function(obj, fireSignal) {\n\t\tif (!obj) return;\n\t\tfireSignal = fireSignal || true;\n\n\t\tif (this.selected !== obj) {\n\t\t\t// deselect previous object\n\t\t\tthis.clearSelection(fireSignal);\n\t\t}\n\t\tif (obj.selected) {\n\t\t\tif (this.toggleSelection) {\n\t\t\t\tif (fireSignal) {\n\t\t\t\t\tthis.onDeselect.dispatch(obj);\n\t\t\t\t}\n\t\t\t\tobj.deselect();\n\t\t\t}\n\t\t}\n\t\telse {\n\t\t\tobj.select();\n\t\t}\n\n\t\tthis.selected = obj;\n\t\tif (fireSignal) {\n\t\t\tthis.onSelect.dispatch(obj);\n\t\t}\n\t},\n\n\tclearSelection: function(fireSignal) {\n\t\tfireSignal = fireSignal || true;\n\t\tif (this.selected) {\n\t\t\tif (fireSignal) {\n\t\t\t\tthis.onDeselect.dispatch(this.selected);\n\t\t\t}\n\t\t\tthis.selected.deselect();\n\t\t}\n\t\tthis.selected = null;\n\t},\n\n\tonMouse: function(type, obj) {\n\t\tswitch (type) {\n\t\t\tcase vg.MouseCaster.DOWN:\n\t\t\t\tif (!obj) {\n\t\t\t\t\tthis.clearSelection();\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase vg.MouseCaster.CLICK:\n\t\t\t\tthis.select(obj);\n\t\t\t\tbreak;\n\t\t}\n\t}\n};\n\nvg.SelectionManager.prototype.constructor = vg.SelectionManager;\n","vg.Tools = {\n\tclamp: function(val, min, max) {\n\t\treturn Math.max(min, Math.min(max, val));\n\t},\n\n\tsign: function(val) {\n\t\treturn val && val / Math.abs(val);\n\t},\n\n\t/**\n\t * If one value is passed, it will return something from -val to val.\n\t * Else it returns a value between the range specified by min, max.\n\t */\n\trandom: function(min, max) {\n\t\tif (arguments.length === 1) {\n\t\t\treturn (Math.random() * min) - (min * 0.5);\n\t\t}\n\t\treturn Math.random() * (max - min) + min;\n\t},\n\n\t// from min to (and including) max\n\trandomInt: function(min, max) {\n\t\tif (arguments.length === 1) {\n\t\t\treturn (Math.random() * min) - (min * 0.5) | 0;\n\t\t}\n\t\treturn (Math.random() * (max - min + 1) + min) | 0;\n\t},\n\n\tnormalize: function(v, min, max) {\n\t\treturn (v - min) / (max - min);\n\t},\n\n\tgetShortRotation: function(angle) {\n\t\tangle %= this.TAU;\n\t\tif (angle > this.PI) {\n\t\t\tangle -= this.TAU;\n\t\t}\n\t\telse if (angle < -this.PI) {\n\t\t\tangle += this.TAU;\n\t\t}\n\t\treturn angle;\n\t},\n\n\tgenerateID: function() {\n\t\treturn Math.random().toString(36).slice(2) + Date.now();\n\t},\n\n\tisPlainObject: function(obj) {\n\t\tif (typeof(obj) !== 'object' || obj.nodeType || obj === obj.window) {\n\t\t\treturn false;\n\t\t}\n\t\t// The try/catch suppresses exceptions thrown when attempting to access the 'constructor' property of certain host objects, ie. |window.location|\n\t\t// https://bugzilla.mozilla.org/show_bug.cgi?id=814622\n\t\ttry {\n\t\t\tif (obj.constructor && !Object.prototype.hasOwnProperty.call(obj.constructor.prototype, 'isPrototypeOf')) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\tcatch (err) {\n\t\t\treturn false;\n\t\t}\n\t\t// If the function hasn't returned already, we're confident that\n\t\t// |obj| is a plain object, created by {} or constructed with new Object\n\t\treturn true;\n\t},\n\n\t// https://github.com/KyleAMathews/deepmerge/blob/master/index.js\n\tmerge: function(target, src) {\n\t\tvar self = this, array = Array.isArray(src);\n\t\tvar dst = array && [] || {};\n\t\tif (array) {\n\t\t\ttarget = target || [];\n\t\t\tdst = dst.concat(target);\n\t\t\tsrc.forEach(function(e, i) {\n\t\t\t\tif (typeof dst[i] === 'undefined') {\n\t\t\t\t\tdst[i] = e;\n\t\t\t\t}\n\t\t\t\telse if (self.isPlainObject(e)) {\n\t\t\t\t\tdst[i] = self.merge(target[i], e);\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tif (target.indexOf(e) === -1) {\n\t\t\t\t\t\tdst.push(e);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t\treturn dst;\n\t\t}\n\t\tif (target && self.isPlainObject(target)) {\n\t\t\tObject.keys(target).forEach(function (key) {\n\t\t\t\tdst[key] = target[key];\n\t\t\t});\n\t\t}\n\t\tObject.keys(src).forEach(function (key) {\n\t\t\tif (!src[key] || !self.isPlainObject(src[key])) {\n\t\t\t\tdst[key] = src[key];\n\t\t\t}\n\t\t\telse {\n\t\t\t\tif (!target[key]) {\n\t\t\t\t\tdst[key] = src[key];\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tdst[key] = self.merge(target[key], src[key]);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\treturn dst;\n\t},\n\n\tnow: function() {\n\t\treturn window.nwf ? window.nwf.system.Performance.elapsedTime : window.performance.now();\n\t},\n\n\tempty: function(node) {\n\t\twhile (node.lastChild) {\n\t\t\tnode.removeChild(node.lastChild);\n\t\t}\n\t},\n\n\t/*\n\t\t@source: http://jsperf.com/radix-sort\n\t */\n\tradixSort: function(arr, idxBegin, idxEnd, bit) {\n\t\tidxBegin = idxBegin || 0;\n\t\tidxEnd = idxEnd || arr.length;\n\t\tbit = bit || 31;\n\t\tif (idxBegin >= (idxEnd - 1) || bit < 0) {\n\t\t\treturn;\n\t\t}\n\t\tvar idx = idxBegin;\n\t\tvar idxOnes = idxEnd;\n\t\tvar mask = 0x1 << bit;\n\t\twhile (idx < idxOnes) {\n\t\t\tif (arr[idx] & mask) {\n\t\t\t\t--idxOnes;\n\t\t\t\tvar tmp = arr[idx];\n\t\t\t\tarr[idx] = arr[idxOnes];\n\t\t\t\tarr[idxOnes] = tmp;\n\t\t\t}\n\t\t\telse {\n\t\t\t\t++idx;\n\t\t\t}\n\t\t}\n\t\tthis.radixSort(arr, idxBegin, idxOnes, bit-1);\n\t\tthis.radixSort(arr, idxOnes, idxEnd, bit-1);\n\t},\n\n\trandomizeRGB: function(base, range) {\n\t\tvar rgb = base.split(',');\n\t\tvar color = 'rgb(';\n\t\tvar i, c;\n\t\trange = this.randomInt(range);\n\t\tfor (i = 0; i < 3; i++) {\n\t\t\tc = parseInt(rgb[i]) + range;\n\t\t\tif (c < 0) c = 0;\n\t\t\telse if (c > 255) c = 255;\n\t\t\tcolor += c + ',';\n\t\t}\n\t\tcolor = color.substring(0, color.length-1);\n\t\tcolor += ')';\n\t\treturn color;\n\t},\n\n\tgetJSON: function(config) {\n\t\tvar xhr = new XMLHttpRequest();\n\t\tvar cache = typeof config.cache === 'undefined' ? false : config.cache;\n\t\tvar uri = cache ? config.url : config.url + '?t=' + Math.floor(Math.random() * 10000) + Date.now();\n\t\txhr.onreadystatechange = function() {\n\t\t\tif (this.status === 200) {\n\t\t\t\tvar json = null;\n\t\t\t\ttry {\n\t\t\t\t\tjson = JSON.parse(this.responseText);\n\t\t\t\t}\n\t\t\t\tcatch (err) {\n\t\t\t\t\t// console.warn('[Tools.getJSON] Error: '+config.url+' is not a json resource');\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tconfig.callback.call(config.scope || null, json);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\telse if (this.status !== 0) {\n\t\t\t\tconsole.warn('[Tools.getJSON] Error: '+this.status+' ('+this.statusText+') :: '+config.url);\n\t\t\t}\n\t\t}\n\t\txhr.open('GET', uri, true);\n\t\txhr.setRequestHeader('Accept', 'application/json');\n\t\txhr.setRequestHeader('Content-Type', 'application/json');\n\t\txhr.send('');\n\t}\n};\n"],"sourceRoot":"/source/"}