MapMaster: A Geography-Based Flag Guessing Game

MapMaster, an open-source geography game combining APIs for an educational and fun experience.

The Evolution of MapMaster

What began as a project for an online React course at MalmΓΆ University in Sweden, originally started as a simple interactive map. Initially, the idea was to create a map where users could click on countries to display information about them. However, the project quickly evolved. The simple map transformed into MapMaster, a flag-guessing game that challenges players to identify countries based on their flags.

Introducing MapMaster 🌍

Welcome to MapMaster, a geography-based flag guessing game that offers both fun and educational insights into the world of flags and countries. By integrating the restcountries.com API and the Google Geocoding API, the game became an interactive learning experience.

The Game’s Genesis

The idea of MapMaster started as a simple assignment but quickly evolved into a full-fledged game. The goal was to use technology not only to create something entertaining but also educational. By combining the Rest Countries API, which provides information about countries and their flags, with Google’s Geocoding API for accurate map interactions, MapMaster became a reality. It’s a perfect blend of learning and playing, where players test their knowledge of world flags in a fun and interactive way.

Adding a Competitive Edge with a Leaderboard

To enhance the game’s engagement, I added a leaderboard, hosted in Supabase. This addition not only brought a competitive element but also turned MapMaster into a platform where geography enthusiasts can compete and learn.

How to Play

The gameplay is simple yet captivating:

  • Players are presented with a flag and have to guess the corresponding country.
  • Points are scored for correct guesses.
  • The game is time-bound, adding an element of excitement.
  • Clues are available, but using them deducts points, adding a strategic layer to the game.

Project Structure

Here’s a glimpse into the structure of MapMaster:

β”œβ”€β”€ LICENSE
β”œβ”€β”€ README.md
β”œβ”€β”€ index.html
β”œβ”€β”€ package.json
β”œβ”€β”€ public
β”‚   └── favicon.svg
β”œβ”€β”€ src
β”‚   β”œβ”€β”€ App.tsx
β”‚   β”œβ”€β”€ api
β”‚   β”‚   β”œβ”€β”€ CountriesApi.ts
β”‚   β”‚   └── GeocodeApi.ts
β”‚   β”œβ”€β”€ assets
β”‚   β”‚   β”œβ”€β”€ fonts
β”‚   β”‚   β”‚   β”œβ”€β”€ RocherColorGX.woff
β”‚   β”‚   β”‚   └── RocherColorGX.woff2
β”‚   β”‚   └── scss
β”‚   β”‚       β”œβ”€β”€ _base.scss
β”‚   β”‚       β”œβ”€β”€ _font.scss
β”‚   β”‚       β”œβ”€β”€ _variables.scss
β”‚   β”‚       β”œβ”€β”€ components
β”‚   β”‚       β”‚   β”œβ”€β”€ buttons.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ clickwindow.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ confetti.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ flag.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ gamemode.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ gameover.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ leaderboard.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ leaderboardentry.scss
β”‚   β”‚       β”‚   β”œβ”€β”€ overlays.scss
β”‚   β”‚       β”‚   └── roundwin.scss
β”‚   β”‚       └── main.scss
β”‚   β”œβ”€β”€ clients
β”‚   β”‚   └── SupaBaseClient.ts
β”‚   β”œβ”€β”€ components
β”‚   β”‚   β”œβ”€β”€ ClickWindow.tsx
β”‚   β”‚   β”œβ”€β”€ ConfettiCanon.tsx
β”‚   β”‚   β”œβ”€β”€ Game.tsx
β”‚   β”‚   β”œβ”€β”€ GameInitializer.ts
β”‚   β”‚   β”œβ”€β”€ GameUtils.ts
β”‚   β”‚   β”œβ”€β”€ Leaderboard.tsx
β”‚   β”‚   β”œβ”€β”€ Map.tsx
β”‚   β”‚   β”œβ”€β”€ Notification.tsx
β”‚   β”‚   β”œβ”€β”€ overlays
β”‚   β”‚   β”‚   β”œβ”€β”€ ClueOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ FlagOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ GameModeSelectionOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ GameOverOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ InstructionsOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ LeaderboardEntryOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ PointsOverlay.tsx
β”‚   β”‚   β”‚   β”œβ”€β”€ RoundWinOverlay.tsx
β”‚   β”‚   β”‚   └── TimerOverlay.tsx
β”‚   β”‚   └── stages
β”‚   β”‚       β”œβ”€β”€ GameModeSelectionStage.tsx
β”‚   β”‚       β”œβ”€β”€ GameOverStage.tsx
β”‚   β”‚       β”œβ”€β”€ InstructionsStage.tsx
β”‚   β”‚       β”œβ”€β”€ RoundWonStage.tsx
β”‚   β”‚       └── RunningStage.tsx
β”‚   β”œβ”€β”€ constants
β”‚   β”‚   β”œβ”€β”€ InitialGameState.ts
β”‚   β”‚   β”œβ”€β”€ constants.ts
β”‚   β”‚   └── overlayVariants.ts
β”‚   β”œβ”€β”€ contexts
β”‚   β”‚   β”œβ”€β”€ GameContext.tsx
β”‚   β”‚   └── NotificationContext.tsx
β”‚   β”œβ”€β”€ hooks
β”‚   β”‚   β”œβ”€β”€ useAntiCheat.ts
β”‚   β”‚   β”œβ”€β”€ useCountdown.ts
β”‚   β”‚   β”œβ”€β”€ useGameManager.ts
β”‚   β”‚   β”œβ”€β”€ useMapInteraction.ts
β”‚   β”‚   β”œβ”€β”€ useNotification.ts
β”‚   β”‚   β”œβ”€β”€ usePreventPinchZoom.ts
β”‚   β”‚   └── useTimer.ts
β”‚   β”œβ”€β”€ interfaces
β”‚   β”‚   β”œβ”€β”€ Country.ts
β”‚   β”‚   β”œβ”€β”€ GameState.ts
β”‚   β”‚   β”œβ”€β”€ HighScore.ts
β”‚   β”‚   └── INotification.ts
β”‚   β”œβ”€β”€ main.tsx
β”‚   β”œβ”€β”€ reducers
β”‚   β”‚   └── GameReducer.ts
β”‚   β”œβ”€β”€ services
β”‚   β”‚   β”œβ”€β”€ CountryService.ts
β”‚   β”‚   └── HighScoreService.ts
β”‚   └── vite-env.d.ts
β”œβ”€β”€ tsconfig.json
β”œβ”€β”€ tsconfig.node.json
β”œβ”€β”€ vite.config.ts
└── yarn.lock

This structure shows the organization and modern tech stack used to build MapMaster. It’s all about creating an engaging, efficient, and scalable game.

Code Quality and Standards

Developing MapMaster, I emphasized code quality by using ESLint with Airbnb’s style guide. This ensures clean, maintainable code, aligning with best practices in JavaScript development. It’s about crafting code that’s as engaging and intuitive as the game itself.


MapMaster, at its core, is a game that combines fun with a bit of learning. It stands as an example of how creative coding can transform a simple idea into an engaging and enjoyable experience. The game is open source, and I welcome everyone to explore, play, and perhaps contribute to its evolution.

Discover the game on GitHub and enjoy the challenge at https://map.christianek.io. Let’s explore the world of flags together!