Compare commits
4 Commits
94b2c6b140
...
361f0536d9
Author | SHA1 | Date | |
---|---|---|---|
361f0536d9 | |||
97652d8e17 | |||
3985bce99d | |||
5090003484 |
BIN
assets/roguelikeIndoor_transparent.png
Normal file
BIN
assets/roguelikeIndoor_transparent.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 35 KiB |
BIN
assets/roguelikeSheet_transparent.png
Normal file
BIN
assets/roguelikeSheet_transparent.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 134 KiB |
@ -147,6 +147,33 @@
|
|||||||
"width":30.3798879567435,
|
"width":30.3798879567435,
|
||||||
"x":656.930237743527,
|
"x":656.930237743527,
|
||||||
"y":411.661417542295
|
"y":411.661417542295
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"height":23.3879051119279,
|
||||||
|
"id":8,
|
||||||
|
"name":"",
|
||||||
|
"properties":[
|
||||||
|
{
|
||||||
|
"name":"event",
|
||||||
|
"type":"string",
|
||||||
|
"value":"transport"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name":"transport_to_coords",
|
||||||
|
"type":"string",
|
||||||
|
"value":"[300, 410]"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name":"transport_to_room",
|
||||||
|
"type":"string",
|
||||||
|
"value":"sampleInside"
|
||||||
|
}],
|
||||||
|
"rotation":0,
|
||||||
|
"type":"",
|
||||||
|
"visible":true,
|
||||||
|
"width":48.4463748747077,
|
||||||
|
"x":518.988751531351,
|
||||||
|
"y":358.61454504956
|
||||||
}],
|
}],
|
||||||
"opacity":1,
|
"opacity":1,
|
||||||
"type":"objectgroup",
|
"type":"objectgroup",
|
||||||
@ -186,7 +213,7 @@
|
|||||||
"y":0
|
"y":0
|
||||||
}],
|
}],
|
||||||
"nextlayerid":4,
|
"nextlayerid":4,
|
||||||
"nextobjectid":8,
|
"nextobjectid":9,
|
||||||
"orientation":"orthogonal",
|
"orientation":"orthogonal",
|
||||||
"renderorder":"right-down",
|
"renderorder":"right-down",
|
||||||
"tiledversion":"1.11.2",
|
"tiledversion":"1.11.2",
|
||||||
|
100
rooms/sample_inside.tmj
Normal file
100
rooms/sample_inside.tmj
Normal file
@ -0,0 +1,100 @@
|
|||||||
|
{ "compressionlevel":-1,
|
||||||
|
"height":8,
|
||||||
|
"infinite":false,
|
||||||
|
"layers":[
|
||||||
|
{
|
||||||
|
"data":[722, 720, 720, 720, 720, 720, 720, 720, 720, 723,
|
||||||
|
778, 894, 895, 895, 895, 895, 895, 895, 896, 778,
|
||||||
|
778, 891, 890, 890, 890, 890, 890, 890, 893, 778,
|
||||||
|
778, 1063, 1005, 1005, 1005, 1005, 1005, 1005, 1006, 778,
|
||||||
|
778, 28373, 28374, 28374, 28374, 28374, 28375, 1005, 28373, 778,
|
||||||
|
778, 1004, 1005, 1005, 1005, 1005, 1005, 1005, 1006, 778,
|
||||||
|
778, 1004, 1005, 1005, 1005, 1005, 1005, 1005, 1006, 778,
|
||||||
|
779, 720, 720, 721, 1004, 1006, 719, 720, 720, 780],
|
||||||
|
"height":8,
|
||||||
|
"id":1,
|
||||||
|
"name":"Tile Layer 1",
|
||||||
|
"opacity":1,
|
||||||
|
"type":"tilelayer",
|
||||||
|
"visible":true,
|
||||||
|
"width":10,
|
||||||
|
"x":0,
|
||||||
|
"y":0
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"draworder":"topdown",
|
||||||
|
"id":3,
|
||||||
|
"name":"Object Layer 1",
|
||||||
|
"objects":[
|
||||||
|
{
|
||||||
|
"height":51.8134715025906,
|
||||||
|
"id":1,
|
||||||
|
"name":"",
|
||||||
|
"properties":[
|
||||||
|
{
|
||||||
|
"name":"event",
|
||||||
|
"type":"string",
|
||||||
|
"value":"transport"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name":"transport_to_coords",
|
||||||
|
"type":"string",
|
||||||
|
"value":"[528, 386]"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name":"transport_to_room",
|
||||||
|
"type":"string",
|
||||||
|
"value":"sampleRoom"
|
||||||
|
}],
|
||||||
|
"rotation":0,
|
||||||
|
"type":"",
|
||||||
|
"visible":true,
|
||||||
|
"width":112.262521588946,
|
||||||
|
"x":264.001973846533,
|
||||||
|
"y":453.984702689366
|
||||||
|
}],
|
||||||
|
"opacity":1,
|
||||||
|
"type":"objectgroup",
|
||||||
|
"visible":true,
|
||||||
|
"x":0,
|
||||||
|
"y":0
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"data":[0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 28302, 28303, 28304, 0, 0, 28204, 0, 0,
|
||||||
|
0, 27995, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0, 28057, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 1358, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
|
||||||
|
"height":8,
|
||||||
|
"id":2,
|
||||||
|
"name":"Tile Layer 2",
|
||||||
|
"opacity":1,
|
||||||
|
"type":"tilelayer",
|
||||||
|
"visible":true,
|
||||||
|
"width":10,
|
||||||
|
"x":0,
|
||||||
|
"y":0
|
||||||
|
}],
|
||||||
|
"nextlayerid":4,
|
||||||
|
"nextobjectid":3,
|
||||||
|
"orientation":"orthogonal",
|
||||||
|
"renderorder":"right-down",
|
||||||
|
"tiledversion":"1.11.2",
|
||||||
|
"tileheight":64,
|
||||||
|
"tilesets":[
|
||||||
|
{
|
||||||
|
"firstgid":1,
|
||||||
|
"source":"..\/tilesets\/kenney_roguelike_base.tsj"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"firstgid":27922,
|
||||||
|
"source":"..\/tilesets\/kenney_roguelike_indoor.tsj"
|
||||||
|
}],
|
||||||
|
"tilewidth":64,
|
||||||
|
"type":"map",
|
||||||
|
"version":"1.10",
|
||||||
|
"width":10
|
||||||
|
}
|
@ -8,7 +8,8 @@ const TILESET_ASSETS = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const ROOM_ASSETS = {
|
const ROOM_ASSETS = {
|
||||||
sampleRoom: "./rooms/sample.tmj"
|
sampleRoom: "./rooms/sample.tmj",
|
||||||
|
sampleInside: "./rooms/sample_inside.tmj"
|
||||||
}
|
}
|
||||||
|
|
||||||
export default class Assets {
|
export default class Assets {
|
||||||
@ -53,7 +54,7 @@ export default class Assets {
|
|||||||
|
|
||||||
loadTileset(name, path) {
|
loadTileset(name, path) {
|
||||||
return fetch(path).then(rsp => rsp.json()).then(json => {
|
return fetch(path).then(rsp => rsp.json()).then(json => {
|
||||||
return this.assetMap[name] = new Tileset(this.game, json, name)
|
return this.assetMap[name] = new Tileset(this.game, json, name, path)
|
||||||
}).then(tileset => this.loadImages(tileset.imagesToLoad))
|
}).then(tileset => this.loadImages(tileset.imagesToLoad))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
33
src/game.js
33
src/game.js
@ -10,7 +10,7 @@ export default class Game {
|
|||||||
this.canvas = canvas
|
this.canvas = canvas
|
||||||
this.ctx = canvas.getContext("2d")
|
this.ctx = canvas.getContext("2d")
|
||||||
this.timestamp = 0
|
this.timestamp = 0
|
||||||
this.player = new Player(this, 200, 200)
|
this.player = new Player(this, 500, 450)
|
||||||
this.actors = [this.player]
|
this.actors = [this.player]
|
||||||
|
|
||||||
this.input = new Input().initialize()
|
this.input = new Input().initialize()
|
||||||
@ -19,7 +19,8 @@ export default class Game {
|
|||||||
this.events = {
|
this.events = {
|
||||||
"log_test": new Event("log_test", () => console.log("Log events work!")),
|
"log_test": new Event("log_test", () => console.log("Log events work!")),
|
||||||
"change_color": new Event("change_color", object => object.setProperty("color", "blue")),
|
"change_color": new Event("change_color", object => object.setProperty("color", "blue")),
|
||||||
"show_message": new Event("show_message", object => this.message = new Message(this, object.getProperty("messageText")))
|
"show_message": new Event("show_message", this.openMessage.bind(this)),
|
||||||
|
"transport": new Event("transport", this.initiateTransport.bind(this))
|
||||||
}
|
}
|
||||||
|
|
||||||
this.message = null
|
this.message = null
|
||||||
@ -43,10 +44,22 @@ export default class Game {
|
|||||||
this.currentRoom.objects.forEach(roomObject => this.actors.push(roomObject))
|
this.currentRoom.objects.forEach(roomObject => this.actors.push(roomObject))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
openMessage(object) {
|
||||||
|
this.message = new Message(this, object.getProperty("messageText"))
|
||||||
|
}
|
||||||
|
|
||||||
closeMessage(message) {
|
closeMessage(message) {
|
||||||
this.message = null
|
this.message = null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
initiateTransport(object) {
|
||||||
|
const coords = JSON.parse(object.getProperty("transport_to_coords"))
|
||||||
|
this.actors = [this.player]
|
||||||
|
this.loadRoom(this.assets.get(object.getProperty("transport_to_room")))
|
||||||
|
this.player.x = coords[0]
|
||||||
|
this.player.y = coords[1]
|
||||||
|
}
|
||||||
|
|
||||||
loop(timestamp) {
|
loop(timestamp) {
|
||||||
this.dt = timestamp - this.timestamp
|
this.dt = timestamp - this.timestamp
|
||||||
const fps = 1000 / this.dt
|
const fps = 1000 / this.dt
|
||||||
@ -71,10 +84,13 @@ export default class Game {
|
|||||||
|
|
||||||
draw() {
|
draw() {
|
||||||
const { canvas, ctx } = this
|
const { canvas, ctx } = this
|
||||||
|
ctx.fillStyle = "black"
|
||||||
|
ctx.fillRect(0, 0, canvas.width, canvas.height)
|
||||||
this.currentRoom.draw(ctx)
|
this.currentRoom.draw(ctx)
|
||||||
this.actors.forEach(actor => actor.draw(ctx))
|
this.actors.forEach(actor => actor.draw(ctx))
|
||||||
this.message?.draw(ctx)
|
this.message?.draw(ctx)
|
||||||
this.drawFps(ctx)
|
this.drawFps(ctx)
|
||||||
|
this.drawPlayerPosition(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
drawFps(ctx) {
|
drawFps(ctx) {
|
||||||
@ -87,4 +103,17 @@ export default class Game {
|
|||||||
ctx.fillText(Math.round(average(this.fpsBuffer)), ctx.canvas.width, 0)
|
ctx.fillText(Math.round(average(this.fpsBuffer)), ctx.canvas.width, 0)
|
||||||
ctx.strokeText(Math.round(average(this.fpsBuffer)), ctx.canvas.width, 0)
|
ctx.strokeText(Math.round(average(this.fpsBuffer)), ctx.canvas.width, 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
drawPlayerPosition(ctx) {
|
||||||
|
if (!this.player) return
|
||||||
|
|
||||||
|
ctx.fillStyle = "white"
|
||||||
|
ctx.fillRect(ctx.canvas.width, 20, -80, 20)
|
||||||
|
ctx.strokeStyle = "black"
|
||||||
|
ctx.textBaseline = "top"
|
||||||
|
ctx.textAlign = "right"
|
||||||
|
ctx.font = "bold 20px serif"
|
||||||
|
ctx.fillText(`${this.player.x}, ${this.player.y}`, ctx.canvas.width, 20)
|
||||||
|
ctx.strokeText(`${this.player.x}, ${this.player.y}`, ctx.canvas.width, 20)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
11
src/room.js
11
src/room.js
@ -70,8 +70,15 @@ export default class Room {
|
|||||||
for (let y = 0; y < layer.height; y++) {
|
for (let y = 0; y < layer.height; y++) {
|
||||||
for (let x = 0; x < layer.width; x++) {
|
for (let x = 0; x < layer.width; x++) {
|
||||||
const index = x + (y * layer.width)
|
const index = x + (y * layer.width)
|
||||||
const tileIndex = layer.data[index] - 1
|
let tileIndex = layer.data[index] + 1
|
||||||
const tileset = this.tilesets[0]
|
if (tileIndex == 1) continue
|
||||||
|
let tileset = this.json.tilesets
|
||||||
|
.sort((a, b) => b.firstgid - a.firstgid)
|
||||||
|
.find(ts => ts.firstgid <= tileIndex)
|
||||||
|
const { firstgid } = tileset
|
||||||
|
tileset = this.tilesets.find(ts => ts.source == tileset.source)
|
||||||
|
tileIndex -= firstgid + 1
|
||||||
|
|
||||||
const [sx, sy] = tileset.tileOffset(tileIndex)
|
const [sx, sy] = tileset.tileOffset(tileIndex)
|
||||||
ctx.drawImage(
|
ctx.drawImage(
|
||||||
tileset.image,
|
tileset.image,
|
||||||
|
@ -1,9 +1,10 @@
|
|||||||
export default class Tileset {
|
export default class Tileset {
|
||||||
constructor(game, json, name) {
|
constructor(game, json, name, source) {
|
||||||
this.game = game
|
this.game = game
|
||||||
this.json = json
|
this.json = json
|
||||||
this.name = name
|
this.name = name
|
||||||
this.tiles = json.tiles
|
this.source = source
|
||||||
|
this.tiles = json.tiles || []
|
||||||
}
|
}
|
||||||
|
|
||||||
get imagesToLoad() {
|
get imagesToLoad() {
|
||||||
@ -30,8 +31,8 @@ export default class Tileset {
|
|||||||
|
|
||||||
tileOffset(index) {
|
tileOffset(index) {
|
||||||
return [
|
return [
|
||||||
((index % this.columns) * this.tileWidth),
|
((index % this.columns) * (this.tileWidth + this.json.spacing)),
|
||||||
(Math.floor(index / this.columns) * this.tileHeight)
|
(Math.floor(index / this.columns) * (this.tileHeight + this.json.spacing))
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,3 +1,7 @@
|
|||||||
body {
|
body {
|
||||||
background-color: #666;
|
background-color: #666;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
canvas {
|
||||||
|
image-rendering: pixelated;
|
||||||
|
}
|
||||||
|
20
tilesets/kenney_roguelike_base.tsj
Normal file
20
tilesets/kenney_roguelike_base.tsj
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
{ "columns":57,
|
||||||
|
"grid":
|
||||||
|
{
|
||||||
|
"height":16,
|
||||||
|
"orientation":"orthogonal",
|
||||||
|
"width":16
|
||||||
|
},
|
||||||
|
"image":"..\/assets\/roguelikeSheet_transparent.png",
|
||||||
|
"imageheight":2104,
|
||||||
|
"imagewidth":3872,
|
||||||
|
"margin":0,
|
||||||
|
"name":"kenney_roguelike_base",
|
||||||
|
"spacing":4,
|
||||||
|
"tilecount":27921,
|
||||||
|
"tiledversion":"1.11.2",
|
||||||
|
"tileheight":64,
|
||||||
|
"tilewidth":64,
|
||||||
|
"type":"tileset",
|
||||||
|
"version":"1.10"
|
||||||
|
}
|
14
tilesets/kenney_roguelike_indoor.tsj
Normal file
14
tilesets/kenney_roguelike_indoor.tsj
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
{ "columns":26,
|
||||||
|
"image":"..\/assets\/roguelikeIndoor_transparent.png",
|
||||||
|
"imageheight":1220,
|
||||||
|
"imagewidth":1828,
|
||||||
|
"margin":0,
|
||||||
|
"name":"kenney_roguelike_indoor",
|
||||||
|
"spacing":4,
|
||||||
|
"tilecount":7597,
|
||||||
|
"tiledversion":"1.11.2",
|
||||||
|
"tileheight":64,
|
||||||
|
"tilewidth":64,
|
||||||
|
"type":"tileset",
|
||||||
|
"version":"1.10"
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user