Skip to content

alex180500/muko-game

Repository files navigation

Müko

Note

This project is under early development. Features, rules, and assets may change over time.

Müko is a two-player strategy game played on an 8x8 (chess) board. It is inspired by Ugolki (also known as Corners), a variation of checkers popular in Eastern Europe.

The game is playable online via shareable invite links, with automatic seat assignment, session persistence, and rematch support.

Caution

Although the core game code is Open Source, all artistic assets, game concept and branding are proprietary. Please see the License & Intellectual Property section at the bottom of this README for details.

🎮 How to Play

Objective

The goal of the game is to move all of your pieces from your starting positions to the opponent's starting positions. There is no capturing in Müko. Pieces remain on the board; the goal is simply to race to the other side.

There are two possible setups in the game, which you can choose when creating a new game.

Rules

  1. Players: Player 0 (White) and Player 1 (Black).
  2. Setup: The game allows two different kinds of setups:
    • 3x3 or Standard - Each player starts with 9 pieces arranged in a 3x3 grid in their respective corner (bottom-left for white, top-right for black).
    • 3x4 or Duygu Variant - Each player starts with 12 pieces arranged in a 3x4 grid in their respective corner.
  3. Movement: Players take turns moving one piece per turn in two possible ways:
    • Slide: Move one square orthogonally (horizontally or vertically) into an empty adjacent square.
    • Jumps: Jump over an adjacent piece (friendly or opponent's) into an empty square immediately beyond it. You can chain multiple jumps in one single movement for big leaps across the board.

Controls

  • Movement: The game is designed to be played with a mouse or touch input.
    • Clicks or touch: select a piece and then select a valid destination square to move.
    • Drag and Drop: You can also drag a piece to a valid destination square to move it.
  • Flip Board: Click the "Flip Board" button to rotate the view (Player 1/Black sees the board flipped by default).
  • Home: Click the House icon to return to the main lobby.

🔗 Lobby & Session System

Joining a Game

When the first player creates a game, they receive a shareable URL (e.g. .../play/K9X2) and can copy it via the Copy Invite Link button in the game header. When the second player opens that link:

  • 0 seats taken → shown a side-picker (White / Random / Black).
  • 1 seat taken → automatically placed on the remaining side with no interaction needed.
  • 2 seats taken → joined as a spectator.

Session Persistence & Reconnection

Each browser is assigned a stable anonymous identity (stored in localStorage). When a player joins a seat, their credentials are saved locally. If the page is refreshed or the browser crashes, re-opening the same URL reconnects them to their seat instantly — no re-joining needed.

Rematch / Play Again

When a game ends, both players see a Play Again button. Either player can initiate:

  1. Click Play Again → a local side-picker appears (White / Random / Black).
  2. Choose a side → a new match is created, the choosing player is pre-joined to their selected seat, and the new match ID is broadcast to the other player via the game's chat channel.
  3. The other player is automatically redirected to the new match and placed on the remaining seat — no interaction required on their end.

If both players click Play Again simultaneously, whoever picks a side first wins; the other is redirected as the auto-joiner.

🏗️ Project Architecture & Deployment

This project is organized as an npm workspaces monorepo with three packages:

muko-game/
  packages/logic/   → Shared game rules (@muko/logic) — raw TypeScript, no build step
  server/           → boardgame.io game server, run directly via tsx
  frontend/         → React/Vite SPA
    src/
      lib/          → Client-side session utilities
        identity.ts        → Stable per-browser anonymous ID (localStorage)
        session.ts         → Per-match credential storage (MatchSession)
        useMatchSession.ts → Hook: reconnect / auto-join / side-picker state machine
      components/
        LobbyView.tsx → Game creation & join-by-code screen
        GameView.tsx  → Match screen, driven by useMatchSession
      Board.tsx       → Game board + rematch logic (sendChatMessage broadcast)

Both the server and frontend consume @muko/logic raw TypeScript source directly — no compilation step is needed for the shared package.

Stack

  • Engine: boardgame.io (State management & Multiplayer)
  • Frontend: React, Vite, TypeScript.
  • Backend: Node.js + Koa (via boardgame.io), run with tsx.
  • Shared Logic: @muko/logic — plain TypeScript, consumed directly by both packages.

Running Locally

To play the game locally, run everything from the monorepo root.

  1. Install dependencies:

    npm install
  2. Start development mode (server + frontend):

    npm run dev

    Server runs on port 8000 and frontend on http://localhost:5173 (typically). No build step is needed — both Vite and the server consume the shared logic package's TypeScript source directly.

  3. Optional — type-check the frontend:

    npm run typecheck -w muko-frontend
  4. Play!

    • Open the link shown in the frontend terminal.
    • Click New Game (Standard or Duygu Variant).
    • Share the URL or use the Copy Invite Link button in the game header. The second player visits the link and is automatically placed on the remaining side.

Note

The lobby system uses localStorage for session persistence. Clearing browser storage will log a player out of their seat. Reloading the page or navigating back to the same match URL will reconnect automatically as long as storage is intact.

Deployment Guide

  1. Backend (Server): Deploy the server/ folder to a Node.js hosting provider (Render, Railway, Heroku).

    • Build Command: npm install
    • Start Command: npm start (runs via tsx, no compilation step needed)
    • Environment Variables:
      • PORT: The server port (defaults to 8000, most providers set this automatically).
      • FRONTEND_URL: The URL of your deployed frontend (for CORS).
  2. Frontend (Client): Deploy the frontend/ folder to a static host (Vercel, Netlify).

    • App Type: Vite
    • Root Directory: frontend/
    • Build Command: npm run build
    • Output Directory: dist
    • Environment Variables:
      • VITE_GAME_SERVER: The full URL of your deployed backend (e.g. https://muko-server.onrender.com).
  3. Final Configuration: In server/index.ts, update the origins array to include your deployed frontend URL.

Note

The frontend must be served over HTTPS in production. crypto.randomUUID() (used to generate the anonymous client ID) requires a secure context; the code includes a getRandomValues-based fallback for plain-HTTP environments (e.g. local network testing on iOS Safari), but HTTPS is strongly recommended.

⚖️ License & Intellectual Property

This project operates under a Dual License model. Please read carefully to understand what you can and cannot do with this repository.

1. The Source Code (Open Source)

The core logic, algorithms, and technical implementation (e.g., JavaScript/TypeScript code, game engine logic) are licensed under the Apache License 2.0. See the LICENSE file for the full legal text.

Tip

You may: Learn from the code, fork it, modify it for your own use and projects, even for commercial use, but for your own distinct projects.

2. The Game Assets & Core Identity (Proprietary / All Rights Reserved)

The "Soul" of the game is NOT Open Source. All artistic assets, including but not limited to:

  • Visuals: Sprites, UI designs, logos, the "Müko" brand name, and any art.
  • Audio: Sound effects and music tracks.
  • Content: Narrative text, specific level configurations, and the overall visual presentation.
  • Core Game Identity: Rules, mechanics, and unique elements that define the game experience.

...are the exclusive property of the creator. Copyright © 2026 Alessandro Romancino. All Rights Reserved.

What this means for you:

  • No Re-hosting: You may NOT host a playable version of this game on a public website (e.g., itch.io, Vercel, personal site) using these assets.
  • No Reselling: You may NOT sell this game or these assets on any platform.
  • No Asset Reuse: You may NOT extract the art or sound to use in your own projects (commercial or non-commercial).
  • Personal Use: You ARE allowed to download, build, and run the game locally on your own machine for educational purposes or personal enjoyment.
  • Code Reuse: You ARE allowed to copy and adapt the source code for your own projects, provided you do not use any of the proprietary assets or branding.

If you have any questions about licensing or usage, please feel free to contact me at alessandro.romancino@gmail.com.

📑 TODO

  • Player nicknames (the MatchSession type already has a playerName field — wire up a name-input step in the side-picker).
  • Persistent accounts & auth (replace the anonymous clientID in identity.ts with a proper JWT/OAuth token; the MatchSession storage structure stays the same).
  • Database with results of games (nicknames, wins/losses) and a point system based on the places of the pieces at the end of the game (e.g., 3 points for each piece in the correct position, 1 point for each piece in the opponent's starting area but not in the correct position).

About

A web checkers game similar inspired from Ugolki

Topics

Resources

License

Stars

Watchers

Forks

Contributors