Build a TypeScript Quiz Game
Build a terminal quiz game to learn core TypeScript fundamentals.
Introduction
30 Second Summary
Quiz games are one of the most satisfying things to build as a programmer. You get instant feedback, clear rules, and a finished product you can actually play.
In this project, you will build a terminal-based quiz game using TypeScript. Your game will ask multiple-choice questions, check answers, track the player's score, and display results at the end.
What You'll Build
A TypeScript program that runs in your terminal, presenting multiple-choice questions and giving the player feedback on every answer.
By the end of this project, you'll have:
- A TypeScript project initialized with npm and configured with strict type checking.
- A working quiz game built with typed data structures, functions, loops, and conditionals.
- Hands-on experience with every core TypeScript concept you'll need for larger projects (interfaces, arrays, template literals, and more).
- Secret Mission: Difficulty levels and a scoring multiplier that rewards harder questions with more points.
Are there any prerequisites?
This is a complete beginner project. You just need VS Code and Node.js installed on your computer. No prior TypeScript experience is required.
Set Up Your TypeScript Project
Every TypeScript project starts with a proper foundation. You need a project folder, a package manager to handle dependencies, and the TypeScript tooling itself.
In this step, you'll create your project folder, configure TypeScript, and confirm everything works by running your first TypeScript file.
In this step, get ready to:
- Create a project folder and install packages.
- Configure TypeScript with a tsconfig.json file.
- Write and run your first TypeScript file.
Create your project folder and install packages
Before writing any code, you need a dedicated folder for your project and a few packages installed. npm (Node Package Manager) handles downloading and tracking these packages for you.
- In VS Code, click Terminal in the top menu bar.
- Click New Terminal.
What is a terminal?
A terminal is a text-based interface where you type commands to interact with your computer. Instead of clicking through menus, you type short instructions to create folders, install software, and run programs.
- Move to your Desktop by running this command:
cd ~/Desktop
- Create your project folder and move into it by running these commands:
mkdir typescript-quiz-game
cd typescript-quiz-game
- Initialize your project with npm by running:
npm init -y
You should see output starting with Wrote to followed by the contents of a generated package.json file.
What does npm init -y do?
This command creates a package.json file, which is the configuration file for any Node.js project. It tracks your project name, version, and which packages you depend on.
The -y flag accepts all the default values so you don't have to answer prompts one by one.
Now you need to open this folder in VS Code so you can edit files and run commands from the right location.
- In VS Code, click File in the top menu bar.
- Click Open Folder.
- Navigate to your Desktop and select the typescript-quiz-game folder.
- Click Open.
Trust the folder
VS Code may ask "Do you trust the authors of the files in this folder?" when you open it. Click Yes, I trust the authors to continue.
You should see package.json listed in the Explorer sidebar on the left. Now open a fresh terminal that's rooted in your project folder.
- Click Terminal in the top menu bar, then click New Terminal.
- Open package.json by clicking on it in the Explorer sidebar.
- Replace the entire contents of the file with this:
{
"name": "typescript-quiz-game",
"version": "1.0.0",
"description": "A TypeScript quiz game for learning fundamentals",
"main": "quiz.ts",
"scripts": {
"start": "tsx quiz.ts"
},
"keywords": [],
"author": "",
"license": "ISC"
}
What do these fields mean?
- name identifies your project in the npm ecosystem.
- main tells Node.js which file is the entry point of your program.
- scripts defines shortcut commands you can run with npm start instead of typing the full command each time.
- Save package.json by pressing Cmd+S (macOS) or Ctrl+S (Windows).
Now install the packages your project needs. TypeScript provides the type system, tsx runs TypeScript files directly, and readline-sync lets your program ask the player questions in the terminal.
- Install TypeScript and tsx as development dependencies by running:
npm install -D typescript tsx
- Install readline-sync and its type definitions by running:
npm install readline-sync @types/readline-sync
After each install completes, you should see a node_modules folder and a package-lock.json file appear in your Explorer sidebar.
Seeing an error during install?
- Check that your terminal is inside the typescript-quiz-game folder. Run pwd (macOS) or cd (Windows) to confirm.
- Make sure you have an internet connection. npm downloads packages from an online registry.
- If you see a permissions error, try closing VS Code and reopening it.
Help me fix an npm install error in my TypeScript project.
Configure TypeScript with tsconfig.json
TypeScript uses a tsconfig.json file to know how strictly to check your code. This file tells VS Code's editor how to highlight errors and provide suggestions as you type.
- In the Explorer sidebar, hover over the file list area and click the New File icon (a page with a + sign).
- Type tsconfig.json as the file name and press Enter.
- Paste the following configuration into the file:
{
"compilerOptions": {
"strict": true,
"target": "ES2022",
"module": "commonjs",
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true
}
}
What do these options do?
- strict enables all strict type-checking options. This catches more bugs at edit time rather than at runtime.
- target sets which version of JavaScript your code compiles to.
- esModuleInterop allows default imports from CommonJS modules. This lets the import readlineSync from "readline-sync" syntax work smoothly.
- Save tsconfig.json.
You won't see a visible change yet. This file works behind the scenes to power VS Code's type checking as you write code in the next steps.
Seeing a red underline in tsconfig.json?
- Make sure every key and string value is wrapped in double quotes. JSON does not allow single quotes.
- Check that you have matching opening and closing curly braces.
Help me fix a JSON syntax error in my tsconfig.json.
Create quiz.ts and verify your setup
Time to confirm everything works end to end. You'll create your main game file and run it with tsx to make sure TypeScript is ready to go.
- In the Explorer sidebar, click the New File icon again.
- Type quiz.ts as the file name and press Enter.
- Add this line to the file:
console.log("Hello, TypeScript!");
What does this line do?
console.log() prints text to the terminal. This is the simplest possible TypeScript program. If this runs successfully, your entire toolchain (Node.js, tsx, and TypeScript) is working correctly.
- Save quiz.ts.
- Run your TypeScript file by entering this command in the terminal:
npx tsx quiz.ts
You should see Hello, TypeScript! printed in your terminal.
What is tsx?
tsx is a tool that runs TypeScript files directly without needing a separate compile step. It handles everything behind the scenes so you can go straight from writing code to seeing results.
npx runs a package from your project's node_modules without needing a global install.
Not seeing Hello, TypeScript! in your terminal?
- Make sure you saved quiz.ts before running the command.
- Check that the file is named exactly quiz.ts (not quiz.js or Quiz.ts).
- Confirm your terminal is in the typescript-quiz-game folder by checking the folder name shown at the start of the terminal prompt.
Help me troubleshoot why npx tsx quiz.ts isn't working.
✔️ Awesome, I've got everything!
Great. Double check you've saved all three files before moving on.
ⓧ I'd like to double check the full code
Here are all three files as they should look at the end of this step.
{
"name": "typescript-quiz-game",
"version": "1.0.0",
"description": "A TypeScript quiz game for learning fundamentals",
"main": "quiz.ts",
"scripts": {
"start": "tsx quiz.ts"
},
"keywords": [],
"author": "",
"license": "ISC"
}
{
"compilerOptions": {
"strict": true,
"target": "ES2022",
"module": "commonjs",
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true
}
}
console.log("Hello, TypeScript!");
Your TypeScript environment is ready. Next up, you'll define the quiz questions using TypeScript interfaces and typed arrays.
Define Your Quiz Data with Types and Interfaces
Your TypeScript project is set up and ready to go. Now it's time to define the data your quiz game will use.
TypeScript's superpower is its type system. In this step, you'll create a blueprint for your quiz questions so TypeScript can catch mistakes before you ever run the code.
In this step, get ready to:
- Define a Question interface to describe the shape of each quiz question.
- Create an array of 5 quiz questions that follow that shape.
- Run the file to confirm everything passes TypeScript's type checks.
Define a Question interface
An interface in TypeScript is like a contract that describes what properties an object must have and what types those properties are. You'll use one to define the exact shape every quiz question must follow.
- Switch back to quiz.ts in VS Code.
- Select all the existing code (the console.log line from the last step) and delete it.
- Replace it with the following import and interface definition:
import readlineSync from "readline-sync";
// Define the shape of a quiz question
interface Question {
question: string;
options: string[];
correctIndex: number;
}
What does this code do?
The import line brings in the readline-sync library, which you'll use later to get input from the player in the terminal.
The Question interface says every quiz question object must have three properties: a question string (the text of the question), an options array of strings (the multiple-choice answers), and a correctIndex number (which option is correct, counting from 0).
- Save quiz.ts.
You won't see output yet. The next chunk adds quiz data that uses this interface.
Seeing a red underline under the import?
Make sure you installed @types/readline-sync in Step 1. Without those type definitions, TypeScript doesn't know what readline-sync exports.
Check that your tsconfig.json has esModuleInterop set to true. This setting allows the import X from "..." syntax to work with CommonJS packages like readline-sync.
Still stuck? Help me fix this red underline on my readline-sync import in quiz.ts.
Create an array of quiz questions
Now that TypeScript knows what a question looks like, you can create an array of question objects. TypeScript will enforce the interface on every single object in the array.
- Add the following array below your interface definition in quiz.ts:
// Quiz data
const questions: Question[] = [
{
question: "What is the capital of France?",
options: ["London", "Berlin", "Paris", "Madrid"],
correctIndex: 2,
},
{
question: "Which planet is known as the Red Planet?",
options: ["Venus", "Mars", "Jupiter", "Saturn"],
correctIndex: 1,
},
{
question: "What is 7 * 8?",
options: ["54", "56", "58", "62"],
correctIndex: 1,
},
{
question: "Which language is TypeScript built on top of?",
options: ["Python", "Java", "JavaScript", "C++"],
correctIndex: 2,
},
{
question: "What year did the first iPhone release?",
options: ["2005", "2006", "2007", "2008"],
correctIndex: 2,
},
];
What does this code do?
The Question[] type annotation tells TypeScript this array can only hold objects that match the Question interface. If you accidentally leave out a property or use the wrong type, TypeScript flags it immediately.
The correctIndex is zero-based. That means the first option is index 0, the second is index 1, and so on. For the first question, correctIndex: 2 points to "Paris" (the third option).
Customise your questions
Feel free to swap these questions for ones about topics you enjoy. Movies, gaming, sports, cooking. As long as each object has a question string, an options array with at least 2 choices, and a valid correctIndex, TypeScript will keep you safe.
- Save quiz.ts.
You'll confirm everything works in the next substep by running the file.
Seeing a type error in VS Code?
Check that every object in the array has all three properties: question, options, and correctIndex. A missing comma between objects or a misspelled property name will also trigger an error.
Make sure correctIndex is a number, not a string. Writing "2" instead of 2 will fail the type check.
Need more help? Help me fix a type error in my questions array.
Run the file to confirm there are no type errors
- Confirm your code has no type errors by running this command in your terminal:
npx tsx quiz.ts
The command should finish with no output and no errors. That means TypeScript is happy with your code.
Why no output?
Your file defines data but doesn't print anything yet. The fact that it runs without errors proves your interface and array are correctly typed. In the next step, you'll add functions that use this data to run the quiz.
Seeing an error when you run the command?
Make sure your terminal is inside the typescript-quiz-game folder. If you're in the wrong directory, tsx won't find quiz.ts.
If the error mentions a type mismatch, scroll up in your terminal to see which line it points to. The line number tells you exactly which property or object is mistyped.
Still stuck? Help me debug this error when running npx tsx quiz.ts.
✔️ Awesome, I've got everything!
Great. Double check you've saved your file before moving on.
ⓧ I'd like to double check the full code
Here's what your complete quiz.ts should look like at this point:
import readlineSync from "readline-sync";
// Define the shape of a quiz question
interface Question {
question: string;
options: string[];
correctIndex: number;
}
// Quiz data
const questions: Question[] = [
{
question: "What is the capital of France?",
options: ["London", "Berlin", "Paris", "Madrid"],
correctIndex: 2,
},
{
question: "Which planet is known as the Red Planet?",
options: ["Venus", "Mars", "Jupiter", "Saturn"],
correctIndex: 1,
},
{
question: "What is 7 * 8?",
options: ["54", "56", "58", "62"],
correctIndex: 1,
},
{
question: "Which language is TypeScript built on top of?",
options: ["Python", "Java", "JavaScript", "C++"],
correctIndex: 2,
},
{
question: "What year did the first iPhone release?",
options: ["2005", "2006", "2007", "2008"],
correctIndex: 2,
},
];
Your quiz data is locked in and type-safe. Next up, you'll build the game logic that reads these questions, presents them to the player, and tracks their score.
Build the Game Logic with Functions
You have your quiz data defined and ready to go. Now you need to build the engine that actually runs the game.
In this step, you'll write two functions: one that asks a single question and checks the answer, and one that loops through all the questions and tracks the player's score.
In this step, get ready to:
- Write the askQuestion function to display questions and check answers.
- Write the runQuiz function to loop through all questions and track the score.
- Run the quiz and play through it in the terminal.
Write the askQuestion function
Each question in your quiz needs to be displayed to the player, accept their input, and check whether they got it right. A function is perfect for this because you can call it once per question without repeating yourself.
- In quiz.ts, scroll to the bottom of the file (below your questions array).
- Add the askQuestion function by copying the following code below your questions array:
// Ask a single question and return whether the player got it right
function askQuestion(q: Question, questionNumber: number): boolean {
console.log(`\nQuestion ${questionNumber}: ${q.question}`);
const answerIndex: number = readlineSync.keyInSelect(q.options, "Your answer:");
if (answerIndex === -1) {
console.log("You skipped this question.");
return false;
}
if (answerIndex === q.correctIndex) {
return true;
} else {
return false;
}
}
What does this code do?
This function takes a Question object and a question number, then handles the entire flow of asking one question.
- readlineSync.keyInSelect(q.options, "Your answer:") displays the answer choices as a numbered list and waits for the player to pick one. It returns the zero-based index of their choice, or -1 if they cancel.
- The function returns true if the player picked the correct index, or false otherwise. The return type : boolean tells TypeScript exactly what this function gives back.
- The q: Question parameter uses your interface as a type annotation. TypeScript guarantees anything passed in matches the Question shape.
What is a type annotation?
In TypeScript, a type annotation is the : type part you see after parameter names and variable names. It tells TypeScript what kind of value to expect.
If you accidentally pass a string where a number is expected, TypeScript catches the mistake before you even run the code. That's the core benefit of static typing.
- Save quiz.ts.
- You won't see a change yet. The next function (runQuiz) will call askQuestion and bring it to life.
Seeing red squiggles in VS Code?
- Check that the function is placed after the closing ]; of your questions array, not inside it.
- Make sure you have the backtick character (`, not a regular quote) around the template literal strings like `\nQuestion ${questionNumber}`.
- Confirm the closing brace } for the function is present at the end.
Help me fix a TypeScript error in my askQuestion function
Write the runQuiz function
Now you need a function that runs the whole game. It will loop through every question in your array, call askQuestion for each one, and keep a running score.
- Add the runQuiz function below the askQuestion function you just wrote:
// Run the full quiz
function runQuiz(): void {
console.log("=== Welcome to the TypeScript Quiz Game! ===");
console.log(`You will be asked ${questions.length} questions. Good luck!\n`);
let score: number = 0;
for (let i = 0; i < questions.length; i++) {
const isCorrect: boolean = askQuestion(questions[i], i + 1);
if (isCorrect) {
score++;
}
}
console.log(`\nYour score: ${score}/${questions.length}`);
}
// Start the game
runQuiz();
What does this code do?
- : void means this function doesn't return anything. It just runs its logic and prints output.
- let score: number = 0 declares a mutable variable with let (instead of const) because the score changes as the game progresses.
- The for loop iterates through each question in the array. The i + 1 converts from zero-based indexing to human-friendly numbering (Question 1, 2, 3...).
- runQuiz() at the bottom is the line that actually starts the game when you run the file.
Why use let instead of const?
In TypeScript, const declares a variable that can never be reassigned. let declares a variable that can change its value.
The score variable starts at 0 and increases each time the player answers correctly. Since its value changes, you need let. If you tried const, TypeScript would throw an error the moment you try to increment it.
- Save quiz.ts.
Seeing a type error on questions[i]?
- Make sure you typed questions[i] with square brackets, not parentheses.
- Confirm that the runQuiz function is placed after (not inside) the askQuestion function.
- Check that runQuiz(); (the function call) is outside both functions, at the very bottom of the file.
Help me fix a type error in my runQuiz function
Play through your quiz
Your game is ready to play. Time to run it and see everything working together.
- Run your quiz game by entering this command in your terminal:
npx tsx quiz.ts
- You should see a welcome message followed by your first question with numbered answer choices.
- Type the number next to your answer and press **Enter** for each question.
- After the last question, you should see your final score printed (e.g. Your score: 4/5).
What should I see?
Your terminal displays the welcome message, then each question with its options listed as numbered items (e.g. [1] London, [2] Berlin, [3] Paris, [4] Madrid). After you pick an answer, the next question appears. Once you finish all 5, you see your total score.
Quiz not running?
- Make sure you saved quiz.ts before running the command.
- Confirm your terminal is in the typescript-quiz-game folder (the one containing quiz.ts).
- If you see a module error about readline-sync, check that you ran npm install readline-sync in a previous step.
Help me get my TypeScript quiz running
✔️ Awesome, I've got everything!
Great. Double check you've saved your file before moving on.
ⓧ I'd like to double check the full code
Here is the full quiz.ts file at this point. Compare yours to this:
import readlineSync from "readline-sync";
// Define the shape of a quiz question
interface Question {
question: string;
options: string[];
correctIndex: number;
}
// Quiz data
const questions: Question[] = [
{
question: "What is the capital of France?",
options: ["London", "Berlin", "Paris", "Madrid"],
correctIndex: 2,
},
{
question: "Which planet is known as the Red Planet?",
options: ["Venus", "Mars", "Jupiter", "Saturn"],
correctIndex: 1,
},
{
question: "What is 7 * 8?",
options: ["54", "56", "58", "62"],
correctIndex: 1,
},
{
question: "Which language is TypeScript built on top of?",
options: ["Python", "Java", "JavaScript", "C++"],
correctIndex: 2,
},
{
question: "What year did the first iPhone release?",
options: ["2005", "2006", "2007", "2008"],
correctIndex: 2,
},
];
// Ask a single question and return whether the player got it right
function askQuestion(q: Question, questionNumber: number): boolean {
console.log(`\nQuestion ${questionNumber}: ${q.question}`);
const answerIndex: number = readlineSync.keyInSelect(q.options, "Your answer:");
if (answerIndex === -1) {
console.log("You skipped this question.");
return false;
}
if (answerIndex === q.correctIndex) {
return true;
} else {
return false;
}
}
// Run the full quiz
function runQuiz(): void {
console.log("=== Welcome to the TypeScript Quiz Game! ===");
console.log(`You will be asked ${questions.length} questions. Good luck!\n`);
let score: number = 0;
for (let i = 0; i < questions.length; i++) {
const isCorrect: boolean = askQuestion(questions[i], i + 1);
if (isCorrect) {
score++;
}
}
console.log(`\nYour score: ${score}/${questions.length}`);
}
// Start the game
runQuiz();
Your quiz works. Next up, you'll add feedback after each question so the player knows immediately whether they got it right, plus a polished final summary with a percentage score.
Add Feedback and Polish
Your quiz game works. Players can answer questions and see a final score. But right now, the experience feels incomplete because players don't know whether they got each question right or wrong until the very end.
In this step, you'll add immediate feedback after every answer and build a polished summary that calculates a percentage score and displays a custom message based on performance.
In this step, get ready to:
- Add correct/wrong feedback after each answer.
- Build a final summary with a percentage score and conditional messages.
- Run the full quiz and verify everything works together.
Add answer feedback to askQuestion
Right now, the askQuestion function silently returns true or false without telling the player what happened. You'll add feedback messages so the player immediately knows whether they were right.
- In quiz.ts, scroll down to the askQuestion function and find the final if/else block that checks whether the answer is correct.
- Find this code:
if (answerIndex === q.correctIndex) {
return true;
} else {
return false;
}
- Replace that entire if/else block with this version that prints feedback before returning:
if (answerIndex === q.correctIndex) {
console.log("Correct!");
return true;
} else {
console.log(`Wrong! The correct answer was: ${q.options[q.correctIndex]}`);
return false;
}
What does this code do?
When the player picks the correct answer, they see "Correct!" right away. When they pick the wrong one, the game tells them which answer was actually right using a template literal to insert the correct option from the array.
Template literals use backticks (`) instead of quotes and let you embed expressions with ${...} syntax. The expression q.options[q.correctIndex] grabs the text of the correct answer from the options array.
Add a polished final summary
The current ending just prints a raw score like "3/5". A good game gives the player a percentage and a message that reflects how they did.
- In the runQuiz function, find this line near the bottom:
console.log(`\nYour score: ${score}/${questions.length}`);
- Replace that single line with the following summary block:
// Final summary
const percentage: number = Math.round((score / questions.length) * 100);
console.log("\n=== Quiz Complete! ===");
console.log(`Your score: ${score}/${questions.length} (${percentage}%)`);
if (percentage === 100) {
console.log("Perfect score! You are a quiz master!");
} else if (percentage >= 70) {
console.log("Great job! You know your stuff!");
} else if (percentage >= 40) {
console.log("Not bad! Keep learning!");
} else {
console.log("Better luck next time! Practice makes perfect.");
}
What does this code do?
The percentage variable divides the score by the total number of questions, multiplies by 100, and rounds it with Math.round() to get a clean whole number.
The if/else if/else chain is conditional logic. TypeScript checks each condition from top to bottom and runs only the first one that is true. This gives the player a different message depending on whether they scored 100%, 70%+, 40%+, or below 40%.
- Save quiz.ts.
Seeing a red underline in VS Code?
Make sure you deleted the old console.log(`\nYour score: ${score}/${questions.length}`); line completely before pasting the new summary block. Having both will cause duplicate variable issues.
Also check that the new code is still inside the runQuiz function's curly braces. If it's outside the function, TypeScript won't have access to the score variable.
Help me fix a TypeScript error in my runQuiz summary code.
Run the full quiz and verify everything works
- Run your quiz by entering this command in the terminal:
npx tsx quiz.ts
- Play through all 5 questions. After each answer, you should see either "Correct!" or "Wrong! The correct answer was: ..." immediately.
- At the end, you should see "=== Quiz Complete! ===", your score as a fraction and percentage, and a message that matches your performance.
What should I see?
If you get 4 out of 5 correct, you'll see something like:
=== Quiz Complete! ===
Your score: 4/5 (80%)
Great job! You know your stuff!
Not seeing feedback after each question?
Make sure the console.log("Correct!") and console.log(`Wrong!...`) lines are inside the if/else block in askQuestion, not in runQuiz. The feedback needs to print inside the function that checks the answer.
Help me debug why my quiz feedback isn't appearing after each question.
✔️ Awesome, I've got everything!
Great. Double check you've saved your file before moving on.
ⓧ I'd like to double check the full code
Here's the complete quiz.ts file. Compare yours against this:
import readlineSync from "readline-sync";
// Define the shape of a quiz question
interface Question {
question: string;
options: string[];
correctIndex: number;
}
// Quiz data
const questions: Question[] = [
{
question: "What is the capital of France?",
options: ["London", "Berlin", "Paris", "Madrid"],
correctIndex: 2,
},
{
question: "Which planet is known as the Red Planet?",
options: ["Venus", "Mars", "Jupiter", "Saturn"],
correctIndex: 1,
},
{
question: "What is 7 * 8?",
options: ["54", "56", "58", "62"],
correctIndex: 1,
},
{
question: "Which language is TypeScript built on top of?",
options: ["Python", "Java", "JavaScript", "C++"],
correctIndex: 2,
},
{
question: "What year did the first iPhone release?",
options: ["2005", "2006", "2007", "2008"],
correctIndex: 2,
},
];
// Ask a single question and return whether the player got it right
function askQuestion(q: Question, questionNumber: number): boolean {
console.log(`\nQuestion ${questionNumber}: ${q.question}`);
const answerIndex: number = readlineSync.keyInSelect(q.options, "Your answer:");
if (answerIndex === -1) {
console.log("You skipped this question.");
return false;
}
if (answerIndex === q.correctIndex) {
console.log("Correct!");
return true;
} else {
console.log(`Wrong! The correct answer was: ${q.options[q.correctIndex]}`);
return false;
}
}
// Run the full quiz
function runQuiz(): void {
console.log("=== Welcome to the TypeScript Quiz Game! ===");
console.log(`You will be asked ${questions.length} questions. Good luck!\n`);
let score: number = 0;
for (let i = 0; i < questions.length; i++) {
const isCorrect: boolean = askQuestion(questions[i], i + 1);
if (isCorrect) {
score++;
}
}
// Final summary
const percentage: number = Math.round((score / questions.length) * 100);
console.log("\n=== Quiz Complete! ===");
console.log(`Your score: ${score}/${questions.length} (${percentage}%)`);
if (percentage === 100) {
console.log("Perfect score! You are a quiz master!");
} else if (percentage >= 70) {
console.log("Great job! You know your stuff!");
} else if (percentage >= 40) {
console.log("Not bad! Keep learning!");
} else {
console.log("Better luck next time! Practice makes perfect.");
}
}
// Start the game
runQuiz();
Your quiz game is complete. Players get instant feedback, a percentage score, and a personalized message at the end. Next up, you can take on the Secret Mission to add difficulty levels and a scoring multiplier.
Secret mission
Add Difficulty Levels and Score Multipliers
Your quiz treats every question the same. But in real games, harder questions should reward the player with more points. Can you extend your TypeScript interface with a union type and build a scoring multiplier system?
Clean Up Your Resources
Clean Up Your Resources
This project runs entirely locally, so there are no ongoing costs. Decide whether to keep your project folder on your computer or delete it entirely.
Resources you used:
- Project folder (typescript-quiz-game) containing quiz.ts, tsconfig.json, package.json, and node_modules.
Keep everything running
No action needed. Choose this if you want to keep your quiz game and continue experimenting with TypeScript.
- Your project folder stays on your Desktop. You can run the quiz any time with npx tsx quiz.ts.
- The node_modules folder takes up some disk space but causes no other impact.
Pause - I'll come back to this later
Since this is a local project with no running processes, there is nothing to pause. Your files will sit quietly on disk until you return.
- If you want to free up disk space from node_modules, you can delete that folder and reinstall later with npm install.
Delete - I don't want to use this again
Remove all project files from your computer. This cannot be undone.
- Close any open files from this project in VS Code.
- Delete the project folder by running the appropriate command for your operating system.
On macOS/Linux:
cd ~/Desktop
rm -rf typescript-quiz-game
On Windows:
cd ~\Desktop
rmdir /s /q typescript-quiz-game
- Confirm the folder is gone by running ls (macOS/Linux) or dir (Windows) on your Desktop. You should no longer see typescript-quiz-game in the output.
That's a Wrap!
That's a Wrap!
Nice work! You just built a fully functional quiz game from scratch in TypeScript. Every core concept you used here (types, interfaces, functions, arrays, loops, conditionals) is the foundation of real-world TypeScript applications.
You've learned how to:
- Built a working TypeScript project from scratch with npm initialization, strict tsconfig.json configuration, and the tsx runner.
- Defined data structures using interfaces and typed arrays to model quiz questions with enforced shapes.
- Wrote interactive game logic with typed functions, conditional feedback (if/else), for loops, and template literals for dynamic output.
- Secret Mission: Extended the interface with a union type for difficulty levels and implemented a point multiplier system that rewards harder questions with more points.
Ready to quiz yourself?