diff --git a/apps/server/src/entities/Player.ts b/apps/server/src/entities/Player.ts new file mode 100644 index 0000000..da5e973 --- /dev/null +++ b/apps/server/src/entities/Player.ts @@ -0,0 +1,15 @@ +// src/entities/Player.ts +export class Player { + public id: string; + public x: number; + public y: number; + public color: string; + + constructor(id: string) { + this.id = id; + this.x = 0; + this.y = 0; + // ランダムな色をつけるとおしゃれです + this.color = '#' + Math.floor(Math.random()*16777215).toString(16); + } +} \ No newline at end of file diff --git a/apps/server/src/index.ts b/apps/server/src/index.ts index 92df8af..bc29276 100644 --- a/apps/server/src/index.ts +++ b/apps/server/src/index.ts @@ -1 +1,30 @@ -console.log("Server is running!"); \ No newline at end of file +// src/index.ts +import { Server } from "socket.io"; +import { createServer } from "http"; // Node.js標準のHTTPサーバー +import { GameManager } from "./managers/GameManager.js"; +import { SocketManager } from "./network/SocketManager.js"; + +const PORT = 3000; + +// HTTPサーバーとSocket.ioサーバーの作成 +const httpServer = createServer(); +const io = new Server(httpServer, { + cors: { + origin: "*", // 開発用:どこからでも許可 + methods: ["GET", "POST"] + }, +}); + +// ゲームマネージャーと通信マネージャーの起動 +const gameManager = new GameManager(); +const socketManager = new SocketManager(io, gameManager); + +socketManager.initialize(); + +// サーバー起動 +httpServer.listen(PORT, () => { + console.log(` + 🚀 Server is running on port ${PORT} + waiting for connections... + `); +}); \ No newline at end of file diff --git a/apps/server/src/managers/GameManager.ts b/apps/server/src/managers/GameManager.ts new file mode 100644 index 0000000..a69454a --- /dev/null +++ b/apps/server/src/managers/GameManager.ts @@ -0,0 +1,38 @@ +// src/managers/GameManager.ts +import { Player } from "../entities/Player.js"; + +export class GameManager { + // IDをキーにしてプレイヤーを保存する + private players: Map; + + constructor() { + this.players = new Map(); + } + + // プレイヤー追加 + addPlayer(id: string): Player { + const player = new Player(id); + this.players.set(id, player); + return player; + } + + // プレイヤー削除 + removePlayer(id: string) { + this.players.delete(id); + } + + // プレイヤー移動 + movePlayer(id: string, x: number, y: number) { + const player = this.players.get(id); + if (player) { + player.x = x; + player.y = y; + } + } + + // 全プレイヤーのリストを返す(通信で送るため) + getAllPlayers() { + // Mapを配列({id, x, y, color}[])に変換 + return Array.from(this.players.values()); + } +} \ No newline at end of file diff --git a/apps/server/src/network/SocketManager.ts b/apps/server/src/network/SocketManager.ts new file mode 100644 index 0000000..0811091 --- /dev/null +++ b/apps/server/src/network/SocketManager.ts @@ -0,0 +1,47 @@ +// src/network/SocketManager.ts +import { Server, Socket } from "socket.io"; +import { GameManager } from "../managers/GameManager.js"; + +export class SocketManager { + private io: Server; + private gameManager: GameManager; + + constructor(io: Server, gameManager: GameManager) { + this.io = io; + this.gameManager = gameManager; + } + + public initialize() { + this.io.on("connection", (socket: Socket) => { + console.log(`✅ User connected: ${socket.id}`); + + // 1. ゲームにプレイヤーを追加 + const player = this.gameManager.addPlayer(socket.id); + + // 2. 参加した本人に「現在の全プレイヤー」を教える + socket.emit("current_players", this.gameManager.getAllPlayers()); + + // 3. 他のみんなに「新しい人が来たよ」と教える + socket.broadcast.emit("new_player", player); + + // --- イベント受信 --- + + // 移動データが来た時 + socket.on("move", (data: { x: number; y: number }) => { + // マネージャーの状態を更新 + this.gameManager.movePlayer(socket.id, data.x, data.y); + + // 全員に位置情報を配信 + // (人数が増えたらここを最適化しますが、まずはこれでOK) + this.io.emit("update_player", { id: socket.id, x: data.x, y: data.y }); + }); + + // 切断した時 + socket.on("disconnect", () => { + console.log(`❌ User disconnected: ${socket.id}`); + this.gameManager.removePlayer(socket.id); + this.io.emit("remove_player", socket.id); + }); + }); + } +} \ No newline at end of file