Saving while it works xD

This commit is contained in:
2021-01-31 02:05:40 +02:00
parent 0780c1ed52
commit c7de79fbc4
19 changed files with 642 additions and 1898 deletions

View File

@@ -1,5 +1,5 @@
import p5 from "p5";
import OtherPlayer from "./OtherPlayer";
import Player from "./Player";
import { Position } from "./types";
export default class Bullet {
@@ -9,7 +9,7 @@ export default class Bullet {
private _position: Position
constructor(
private _shooter: OtherPlayer,
private _shooter: Player,
private direction: Position,
) {
this._position = {..._shooter.position}

View File

@@ -4,16 +4,32 @@ import OtherPlayer from "./OtherPlayer";
import UserPlayer from "./UserPlayer";
import { PlayerDescription } from "./socketDataTypes";
import Pickable from "./Pickable";
import Player from "./Player";
import PlayerList from "./PlayerList";
import p5 from "p5";
export default class Game {
private player: UserPlayer
private otherPlayers: OtherPlayer[] = []
private bullets: Bullet[] = []
private _otherPlayers: PlayerList
private items: Pickable[] = []
private images: Map<string, p5.Image> = new Map<string, p5.Image>()
constructor(_socket: SocketIOClient.Socket) {
this.player = new UserPlayer(_socket.id, _socket, '', {x:0, y:0}, 'white', new Map<number, boolean>(), 100)
this.player = new UserPlayer(_socket,_socket.id, 'Player', {x:0, y:0}, 'white', new Map<number, boolean>(), 100, 10, 10)
this._otherPlayers = new PlayerList()
}
setImages(images: Map<string, p5.Image>) {
this.images = images
}
getImages() {
return this.images
}
get otherPlayers() {
return this._otherPlayers
}
addItem(item: Pickable) {
@@ -24,6 +40,12 @@ export default class Game {
return this.items
}
removeItemById(id: string) {
this.items = this.items.filter((item) => {
return item.id !== id
})
}
removeItem(pickable: Pickable) {
this.items = this.items.filter((item) => {
return item !== pickable
@@ -34,45 +56,4 @@ export default class Game {
return this.player
}
setPlayer(description: PlayerDescription) {
this.player.id = description.id
this.player.name = description.name
this.player.position = description.position
this.player.color = description.color
}
addOtherPlayer(player: OtherPlayer) {
if (player.id === this.player.id) return
let oPlayer = this.otherPlayers.find((otherPlayer) => {
return player.id === otherPlayer.id
})
if (oPlayer) {
oPlayer.color = player.color
oPlayer.id = player.id
oPlayer.name = player.name
oPlayer.position = player.position
} else {
this.otherPlayers.push(player)
}
}
removeOtherPlayer(id: string) {
this.otherPlayers = this.otherPlayers.filter((player) => {
return player.id !== id
})
}
getOtherPlayers() {
return this.otherPlayers
}
getOtherPlayer(id: string) {
for (let player of this.otherPlayers) {
if (player.id === id) {
return player
}
}
return null
}
}

View File

@@ -4,12 +4,17 @@ import { Position } from "./types";
export default class Pickable {
constructor(
private _id: string,
private _position: Position,
private _item: Item,
) {
}
get id() {
return this._id
}
get position() {
return this._position
}

View File

@@ -0,0 +1,183 @@
import { Position } from './types'
import p5 from 'p5'
import Bullet from './Bullet'
export default class Player {
private KEY_W = 87
private KEY_A = 65
private KEY_S = 83
private KEY_D = 68
private MOVEMENT_SPEED = 0.8
private bullets: Bullet[] = []
constructor(
private _id: string,
private _name: string = 'Player',
private _position: Position = {x: 0, y: 0},
private _color: string = '#ffffff',
private _keysPressed: Map<number, boolean> = new Map<number, boolean>(),
private _health: number = 100,
private _damage: number = 10,
private _defence: number = 10,
) {
this._keysPressed = new Map<number, boolean>()
}
get keysPressed() {
return this._keysPressed
}
get id() {
return this._id
}
set id(id: string) {
this._id = id
}
get name() {
return this._name
}
set name(name: string) {
this._name = name
}
get position() {
return this._position
}
set position(position: Position) {
this._position = position
}
get color() {
return this._color
}
set color(color: string) {
this._color = color
}
get health() {
return this._health
}
set health(health: number) {
this._health = health
}
get damage() {
return this._damage
}
set damage(damage: number) {
this._damage = damage
}
get defence() {
return this._defence
}
set defence(defence: number) {
this._defence = defence
}
hit(bullet: Bullet, socket: SocketIOClient.Socket) {
bullet.timeToLive = -1
let dmg = bullet.shooter.damage - this.defence
if (dmg < 0) dmg = 0
this.health -= dmg
socket.emit('hit-player', {id: this.id, health: this.health})
}
keyAction(key: number, isDown: boolean) {
this._keysPressed.set(key, isDown)
}
takeDamage(damage: number) {
let dmg = damage - this._defence
if (dmg < 0) { dmg = 0 }
this._health -= dmg
}
getPlayerDescription() {
return {
name: this.name,
color: this.color,
position: this.position,
id: this._id,
health: this.health,
damage: this.damage,
defence: this.defence
}
}
move(delta: number) {
if (this.keysPressed.get(this.KEY_A)) {
this.position.x -= this.MOVEMENT_SPEED * delta
}
if (this.keysPressed.get(this.KEY_D)) {
this.position.x += this.MOVEMENT_SPEED * delta
}
if (this.keysPressed.get(this.KEY_W)) {
this.position.y -= this.MOVEMENT_SPEED * delta
}
if (this.keysPressed.get(this.KEY_S)) {
this.position.y += this.MOVEMENT_SPEED * delta
}
if (this.position.x < -1600) {
this.position.x = -1600
}
if (this.position.y < -2000) {
this.position.y = -2000
}
if (this.position.x > 1500) {
this.position.x = 1500
}
if (this.position.y > 1900) {
this.position.y = 1900
}
}
draw(p5: p5, position: Position) {
p5.stroke(0, 0, 0)
p5.strokeWeight(5)
p5.fill(this.color)
p5.ellipse(position.x, position.y, 80, 80)
p5.textSize(32)
p5.fill(255, 255, 255)
p5.textAlign(p5.CENTER, p5.CENTER)
p5.text(this.name, position.x - 300, position.y - 150, 600, 50)
p5.noStroke()
p5.fill('#850000')
p5.rect(position.x - 50, position.y - 90, 100, 5)
p5.fill('#008500')
p5.rect(position.x - 50, position.y - 90, this.health, 5)
}
addBullet(bullet: Bullet) {
this.bullets.push(bullet)
}
getBullets() {
return this.bullets
}
removeExpiredBullets() {
this.bullets = this.bullets.filter((bullet: Bullet) => {
return bullet.timeToLive > 0
})
}
}

28
client/src/PlayerList.ts Normal file
View File

@@ -0,0 +1,28 @@
import Player from "./Player";
export default class PlayerList {
private players: Map<string, Player>
constructor() {
this.players = new Map<string, Player>()
}
getPlayer(id: string) {
return this.players.get(id)
}
getPlayers() {
return this.players
}
addPlayer(id: string, player: Player) {
if (this.players.has(id)) return
this.players.set(id, player)
}
removePlayer(id: string) {
this.players.delete(id)
}
}

View File

@@ -1,20 +1,21 @@
import SocketIOClient from "socket.io-client";
import Bullet from "./Bullet";
import OtherPlayer from "./OtherPlayer";
import Player from "./Player";
import { Position } from "./types";
export default class UserPlayer extends OtherPlayer{
export default class UserPlayer extends Player {
constructor(
_id: string,
private _socket: SocketIOClient.Socket,
_id: string,
_name: string,
_position: Position,
_color: string,
_keysPressed: Map<number, boolean>,
_health: number
_health: number,
_damage: number,
_defence: number
) {
super(_id, _name, _position, _color, _keysPressed, _health)
super(_id, _name, _position, _color, _keysPressed, _health, _damage, _defence)
}
get socket(): SocketIOClient.Socket {
@@ -22,10 +23,12 @@ export default class UserPlayer extends OtherPlayer{
}
keyUp(key: number) {
this.keysPressed.set(key, false)
this.socket.emit('key-action', {key: key, isDown: false})
}
keyDown(key: number) {
this.keysPressed.set(key, true)
this.socket.emit('key-action', {key: key, isDown: true})
}

View File

@@ -9,9 +9,10 @@ import Bullet from './Bullet'
import { Position } from './types'
import Pickable from './Pickable'
import Item from './Item'
import * as uuid from 'uuid'
const socket = io("https://blobbystrike.ioi.lt", {secure: true})
const game = new Game(socket)
let socket: SocketIOClient.Socket
let game: Game
let images: Map<string, P5.Image>
let fonts: Map<string, P5.Font>
@@ -40,18 +41,15 @@ const getDeltaTime = () => {
return dt
}
function onKeyDown(e: any) {
game.getPlayer().keyDown(e.keyCode)
game.getPlayer().setKeyPressed(e.keyCode, true)
}
function onKeyUp(e: any) {
game.getPlayer().keyUp(e.keyCode)
game.getPlayer().setKeyPressed(e.keyCode, false)
}
function onContextMenu() {
game.getPlayer().clearKeysPressed()
game.getPlayer().keysPressed.clear()
}
function getCursorPosition(canvas: HTMLCanvasElement, event: MouseEvent) {
@@ -72,11 +70,11 @@ function onMouseUp(e: MouseEvent) {
pos.y -= parseInt(canvas.style.height) / 2
let length = Math.sqrt((pos.x * pos.x) + (pos.y * pos.y))
let scale = 1 / length
scale *= 5
scale *= 2
pos.x *= scale
pos.y *= scale
game.getPlayer().addBullet(new Bullet(game.getPlayer(), pos))
socket.emit('shoot', {position: game.getPlayer().position, direction: pos})
socket.emit('shoot', {id: game.getPlayer().id, position: game.getPlayer().position, direction: pos})
}
function onCanvasResize() {
@@ -138,9 +136,18 @@ function drawMap(p5: P5) {
const sketch = (p5: P5) => {
p5.preload = () => {
let resources = prealoadResources(p5)
images = resources.images
fonts = resources.fonts
}
p5.setup = () => {
buildMap()
p5.createCanvas(1920, 1080);
p5.createCanvas(1920, 1080)
canvas = document.querySelector('canvas')!
onCanvasResize()
window.addEventListener('resize', onCanvasResize)
@@ -150,16 +157,9 @@ const sketch = (p5: P5) => {
canvas.addEventListener("mousedown", onMouseUp)
p5.textFont(fonts.get('Ubuntu')!)
game.addItem(new Pickable({x: 150, y: 150}, new Item(images.get('healthPack')!, "HEAL")))
game.addItem(new Pickable({x: 150, y: 100}, new Item(images.get('powerUp')!, "DAMAGE")))
game.addItem(new Pickable({x: 150, y: 100}, new Item(images.get('shield')!, "DEFENCE")))
}
p5.preload = () => {
let resources = prealoadResources(p5)
images = resources.images
fonts = resources.fonts
socket = io("https://blobbystrike.ioi.lt", {secure: true})
game = new Game(socket)
game.setImages(images)
setupSocketEvents(socket, game)
}
@@ -168,12 +168,12 @@ const sketch = (p5: P5) => {
let dt = getDeltaTime()
p5.background('#000000')
p5.background('#690000')
p5.translate(p5.width/2, p5.height/2)
// drawing map background
drawMap(p5)
// drawMap(p5)
// drawing items
@@ -183,24 +183,24 @@ const sketch = (p5: P5) => {
switch(item.item.type) {
case "HEAL":
game.getPlayer().health = 100
socket.emit('item-heal')
break;
case "DAMAGE":
game.getPlayer().damage += 2
socket.emit('item-damage')
break;
case "DEFENCE":
game.getPlayer().defence += 2
socket.emit('item-defence')
socket.emit('item-picked', {id: item.id})
socket.emit('hit-player', {id: game.getPlayer().id, health: game.getPlayer().health})
break;
// case "DAMAGE":
// game.getPlayer().damage += 2
// socket.emit('item-damage')
// break;
// case "DEFENCE":
// game.getPlayer().defence += 2
// socket.emit('item-defence')
// break;
}
game.removeItem(item)
}
}
for (let otherPlayer of game.getOtherPlayers()) {
game.otherPlayers.getPlayers().forEach((otherPlayer) => {
// going through other player list
// draw player if in range
@@ -209,6 +209,9 @@ const sketch = (p5: P5) => {
x: otherPlayer.position.x - game.getPlayer().position.x,
y: otherPlayer.position.y - game.getPlayer().position.y
})
// move player if in range (guessing where player will be when request from servers comes back)
otherPlayer.move(dt)
}
// going through bullets of that player
@@ -231,19 +234,19 @@ const sketch = (p5: P5) => {
}
// check if bullet collides with other player
for (let otherPlayerCheck of game.getOtherPlayers()) {
game.otherPlayers.getPlayers().forEach((otherPlayerCheck) => {
if (distance(otherPlayerCheck.position, bullet.position) < BULLET_SIZE + PLAYER_SIZE) {
// check if player bullet collides with is not the player who shot the bullet
if (otherPlayerCheck.id !== bullet.shooter.id) {
bullet.timeToLive = -1
}
}
}
})
}
// removig bullets that has traveled far enough
otherPlayer.removeExpiredBullets()
}
})
// drawing current player
game.getPlayer().draw(p5, {x: 0, y: 0})
@@ -264,12 +267,13 @@ const sketch = (p5: P5) => {
bullet.move(dt)
// check if bullet collides with other player
for (let otherPlayer of game.getOtherPlayers()) {
game.otherPlayers.getPlayers().forEach((otherPlayer) => {
if (otherPlayer.id === game.getPlayer().id) return
if (distance(otherPlayer.position, bullet.position) < BULLET_SIZE + PLAYER_SIZE) {
// register hit to other player
otherPlayer.hit(bullet, game.getPlayer().socket)
}
}
})
}
// removig bullets that has traveled far enough
@@ -282,7 +286,12 @@ const sketch = (p5: P5) => {
p5.text(Math.floor(game.getPlayer().position.x) + ':' + Math.floor(game.getPlayer().position.y), -p5.width/2 + 10, -p5.height/2 + 10)
// moving player depending on keys pressed
let previousePosition = {...game.getPlayer().position}
game.getPlayer().move(dt)
let newPosition = {...game.getPlayer().position}
if (previousePosition.x !== newPosition.x || previousePosition.y !== newPosition.y) {
game.getPlayer().socket.emit('player-moved', {position: newPosition})
}
}
}

View File

@@ -9,8 +9,8 @@ export default function prealoadResources(p5: P5): {
let fonts = new Map<string, P5.Font>()
images.set('grass', p5.loadImage('images/grass.jpg'))
images.set('powerUp', p5.loadImage('images/PowerUp.png'))
images.set('shield', p5.loadImage('images/Shield.png'))
// images.set('powerUp', p5.loadImage('images/PowerUp.png'))
// images.set('shield', p5.loadImage('images/Shield.png'))
images.set('healthPack', p5.loadImage('images/HealthPack.png'))
fonts.set('Ubuntu', p5.loadFont('fonts/Ubuntu/Ubuntu-Regular.ttf'))

View File

@@ -2,7 +2,10 @@ import SocketIOClient from 'socket.io-client'
import Bullet from './Bullet'
import { getCookie } from './Cookie'
import Game from './Game'
import Item from './Item'
import OtherPlayer from './OtherPlayer'
import Pickable from './Pickable'
import Player from './Player'
import { BulletData, PlayerDescription } from './socketDataTypes'
import { Position } from './types'
@@ -10,7 +13,7 @@ export default function setupSocketEvents(socket: SocketIOClient.Socket, game: G
socket.on('greetings', () => {
socket.emit('greetings', {name: getCookie('player-name')})
})
})
socket.on('your-info', function (playerData: PlayerDescription) {
let player = game.getPlayer()
@@ -22,54 +25,90 @@ export default function setupSocketEvents(socket: SocketIOClient.Socket, game: G
socket.emit('get-other-players')
})
socket.on('players-info', function (playersData: PlayerDescription[]) {
for (let playerData of playersData) {
game.addOtherPlayer(new OtherPlayer(playerData.id, playerData.name, playerData.position, playerData.color, new Map<number, boolean>(), playerData.health))
socket.on('new-player-joined', function (playerData: PlayerDescription) {
if (game.getPlayer().id !== playerData.id) {
let oPlayer = game.otherPlayers.getPlayer(playerData.id)
if (oPlayer) {
oPlayer.name = playerData.name
oPlayer.position = playerData.position
oPlayer.color = playerData.color
oPlayer.health = playerData.health
oPlayer.damage = playerData.damage
oPlayer.defence = playerData.defence
} else {
game.otherPlayers.addPlayer(playerData.id, new Player(playerData.id, playerData.name, playerData.position, playerData.color, playerData.keysPressed, playerData.health, playerData.damage, playerData.defence))
}
}
})
socket.on('new-player-joined', function (playerData: PlayerDescription) {
if (game.getPlayer().id !== playerData.id) {
game.addOtherPlayer(new OtherPlayer(playerData.id, playerData.name, playerData.position, playerData.color, new Map<number, boolean>(), playerData.health))
}
})
socket.on('player-moved', function (movedPlayerData: {id: string, position: Position}) {
for (let playerData of game.getOtherPlayers()) {
if (movedPlayerData.id === playerData.id) {
playerData.position = movedPlayerData.position;
}
let otherPlayer = game.otherPlayers.getPlayer(movedPlayerData.id)
if (otherPlayer) {
otherPlayer.position = movedPlayerData.position
}
if (game.getPlayer().id === movedPlayerData.id) {
game.getPlayer().position = movedPlayerData.position
}
})
socket.on('player-disconnected', function (disconnectedPlayer: string) {
game.removeOtherPlayer(disconnectedPlayer)
game.otherPlayers.removePlayer(disconnectedPlayer)
})
socket.on('key-action', (data: {id: string, key: number, isDown: boolean}) => {
let player = game.otherPlayers.getPlayer(data.id)
if (player) {
player.keysPressed.set(data.key, data.isDown)
}
})
socket.on('hit-player', (data: {id: string, health: number}) => {
let player = game.otherPlayers.getPlayer(data.id)
if (player) {
player.health = data.health
}
if (game.getPlayer().id === data.id) {
game.getPlayer().health = data.health
}
})
socket.on('shoot', (data: BulletData) => {
let otherPlayer = game.getOtherPlayer(data.id)
let otherPlayer = game.otherPlayers.getPlayer(data.id)
if (otherPlayer) {
otherPlayer.addBullet(new Bullet(otherPlayer, data.direction))
}
})
socket.on('ded', (data: BulletData) => {
socket.on('disconnect', () => {
window.location.href = '/ded';
})
socket.on('health-update', (data: {id: string, health: number}) => {
let otherPlayer = game.getOtherPlayer(data.id)
if (otherPlayer) {
otherPlayer.health = data.health
}
if (game.getPlayer().socket.id === data.id) {
game.getPlayer().health = data.health
if (data.health <= 0) {
game.getPlayer().socket.disconnect()
window.location.href = '/ded';
}
socket.on('ded', () => {
window.location.href = '/ded';
})
socket.on('new-item', (data: {id: string, position: Position, item: {image: 'healthPack', type: "HEAL"}}) => {
let image = game.getImages().get(data.item.image)
if (image) {
game.addItem(new Pickable(data.id, data.position, new Item(image, data.item.type)))
}
})
socket.on('item-picked', (data: {id: string}) => {
game.removeItemById(data.id)
})
// socket.on('health-update', (data: {id: string, health: number}) => {
// let otherPlayer = game.getOtherPlayer(data.id)
// if (otherPlayer) {
// otherPlayer.health = data.health
// }
// if (game.getPlayer().socket.id === data.id) {
// game.getPlayer().health = data.health
// if (data.health <= 0) {
// game.getPlayer().socket.disconnect()
// window.location.href = '/ded';
// }
// }
// })
}

View File

@@ -9,6 +9,9 @@ export type PlayerDescription = {
},
id: string,
health: number,
damage: number,
defence: number,
keysPressed: Map<number, boolean>
}
export type BulletData = {