Designing a Room in a Text-Based Adventure Game

We have come to the part in our project where our main focus is shifting to the story. This is what makes any work of interactive fiction a game – without the story, there is no game. Storytelling in a text-based adventure is largely done through environmental storytelling; there are no visuals (other than ASCII art on occasion), no narrator to guide the player, and few (if any) other characters to interact with. This makes the design of the rooms and the objects within them crucial to the experience; designing such rooms, the basic building block in any text-based adventure game, will be my main focus going forward.

Deciding what types of rooms make sense for the environment is one of the first steps alongside creating a map to aid in development. It is important to remember that users will not have a map in-game, and so the order of the rooms must be logical without being too complicated. I started to lay out the beginnings of a map in the past week for our game:

A map of the layout of the rooms in our game. The courtyard to the west leads to a flooded chamber, an underground passage, and then an armory. To the east, it leads to an astronomy room, both a study and a room of doors, and a mushroom forest.
First map iteration for our text-based adventure game.

I added an underground passage coming from the flooded chamber since it seems to me that the flooded chamber would already be partially underground. West of that, there is an armory due to it having easy access to the outdoors via the passage (I imagined in its prime, this castle would use that as a secret passage). To the east of the courtyard, the astronomy room leads to some curious places – I thought of this as the research wing, and so I added a wizard’s study, a room of doors (a curious room that appears as a void with doors in all directions), and a mushroom forest (a callback to the glowing mushrooms in the courtyard seen earlier).

As for the tower, that is also a callback: when the user first enters the game, they appear in the courtyard where a large tower looms in the distance looking strangely untouched compared to the rest of the castle. What is it doing there? Why is it not partially in ruins like the rest of the castle? Due to this oddity, it seemed like it could be the location of the logical endpoint to the game.

There is much more to come for this game’s story – and I will avoid giving too many more spoilers from now on! In the meantime, I hope this glimpse into our story-building process was interesting and inspires creativity for those who are working on their own stories too.

Reaching the Midpoint and Our Demo

This week marked the midway point for my team’s text-based adventure game project. The prior week passed by in a blur as we worked hard to get it ready for a demo – after getting the needed functionalities done or close to done, it was time to put all of the pieces together! And I am happy to report that the process was surprisingly seamless. As the writer of the script that runs the game, I was the first who got to actually run the game, and the excitement I felt at seeing it all work so well together was palpable. There is almost nothing so satisfying as seeing a well thought-out plan come together, especially after so much work!

To celebrate our success (and live up to my word), I would like to present a short playthrough video of our demo to show off most of our game’s current features. Enjoy!

A playthrough of our demo showcasing most features.

In the coming weeks, we will be adding the final touches to the game such as adding many more rooms, bringing the story together, and fully implementing save/load functionality. I am excited to dive in to the final stretch after taking a much deserved day off.

Room Objects and JSON Files

As mentioned in previous posts, my team for our capstone project is creating a text-based adventure game using Python. It has been a lot of fun diving into the code and designing this project – and next week we will showcase our first demo! Because of this, our team has been spending a lot of time getting some of the final basic functionalities in place. One of those functionalities is loading data for the rooms in the adventure from external JSON files. And since I have been working on this functionality for the majority of the week, I wanted to share a bit of my process as well as a cool package I plan on using for validating the file structures.

To give context, the foundation of our project rests on game object classes we have created – the Game, Rooms, Doors, and Items. And so, the basic steps for loading up the game from external files are:

  1. Find all of the JSON room files in the rooms folder.
  2. For each file, validate that it is structured correctly (more on this later).
  3. If it is structured correctly, use the data to create a dictionary of Door objects and a dictionary of Item objects.
  4. Use these dictionaries along with the rest of the data to create a new Room object.
  5. Add that Room to the rooms dictionary (which is what is returned).

Luckily, loading the external files and creating the objects was not too difficult of a task once we decided on how we wanted the JSON files to be structured. Because of this, the code for the actual load_rooms function itself was fast to write. What took the most time by far was writing the tests for the function once it was complete. I knew that ideally, I wanted a couple of test JSON files to be created automatically for the testing, and then removed after the tests were done running. This led me down a rabbit hole re-learning how to use unittest’s tearDownClass() class method, and the file creation/deletion took a while due in part to having to remind myself how os.path.abspath(path) works. (Hint: it returns a string of the path to the argument relative to the current working directory; and your cwd changes when you are running tests in another folder versus when you are running the main script files.) Once I remembered this, it was mostly smooth sailing getting the rest of the tests written (even if it did take a while).

So far, everything that I have mentioned is something I have done before, and so I was never completely lost. However, there is something new I will be trying for this part of the project that is uncharted territory for me: validating the JSON data for the correct structure.

While finishing up the load_rooms function, I realized it would be important for us to be able to easily verify that each of the Room files we add were using the correct structure. One way to verify the structure would be to manually go through and check for every key – and sure, this would be doable – but there must be a better way, right?

Enter JSON Schema and Python’s jsonschema library.

“When you’re talking about a data format, you want to have metadata about what keys mean, including the valid inputs for those keys. JSON Schema is a proposed IETF standard how to answer those questions for data.”

From the JSON Schema website – Getting Started Step-By-Step

JSON Schema can be used to validate that a data set adheres to a given schema – and the jsonschema Python library is an implementation of this standard. By using this, it will make it much easier for my team and I to ensure that we are not making any major mistakes when adding new rooms to our game. Trying something new like this is always a bit exciting and I am eager to get started on the actual code for it.

Overall, this week has had its fill of triumphs and trials, and while some of the hurdles took a while to get over, I am satisfied with what I learned and accomplished. By this time next week, I hope to have a demo worthy of showcasing on my blog!

I Used All My Brainpower Writing Descriptions For Testing Room Objects

When I sat down to write this blog post, trusting that my brain is usually good at coming up with words, I was confronted with utter silence. Absolute nothingness. Why is this, you may ask? Well, during my time working on our capstone project yesterday – a text-based adventure game – I spent a significant amount of time implementing the Room class to be used for representing rooms and their contents in our game. And, since Rooms require a short description and a long description, when writing the tests for the Room class, I had to come up with these descriptions. A lot of descriptions. And I may have had too much fun. I would like to share a few of my favorites:

Room Name: “Kitchen”
Short Description: “The floor and the walls are full of potatoes. How this happened is a mystery.”
Long Description: “With the sparkling clean appliances and empty shelves, one would almost believe that this kitchen had never been touched…if it were not for the potatoes. The entire floor is covered in potatoes. And, if one looks closely enough, a hole in the wall reveals that the walls, too, are full of potatoes. How this could have happened is a mystery.”

Room Name: “Chair Hell”
Short Description: “The chairs are staring at you. You feel a sense of dread.”
Long Description: “You are not entirely certain what you did to deserve this – perhaps you were a bit too critical of your office chairs in life – but in this afterlife, you seem to be surrounded by chairs. And not just any chairs – sentient, angry chairs. They look at you with clear malice in their eyes. You wonder if it’s too late to repent.”

Room Name: “Sewing Room”
Short Description: “Fabric is spilling out of the shelves while a mouse is hard at work sewing a button on a sleeve.”
Long Description: “The way the mouse on a nearby table scrutinizes your outfit makes you feel underdressed. Other than the overflowing fabric in the nearby shelves, most of the floor space is taken up by mannequins of various shapes and sizes. About a dozen mice are hard at work doing various repairs, from missing buttons to rips in seams. You wonder who these clothes are for.”

Writing the descriptions was a fun exercise in creative writing – and who knows, perhaps we will use one of these in our final game? And the tests served their purpose as well, all verifications of the currently implemented methods passing on the first try (always satisfying). I even got to use unittest’s Mock class to mock the unfinished Item and Door classes – something I learned about in CS 362 (Software Engineering II) but never had the chance to try. Overall, it was a gratifying exercise, even if my mind is currently out of creativity.

For now, I will make myself a cup of tea and allow my mind some rest until I tackle our project’s Item class – and come up with all of the names and descriptions for those. (Sure, I could use some classic lorem ipsum, but where is the fun in that?)

New Discoveries and Old Adventures

Over the course of the past week, I and a few others in my capstone course were chosen to create a text-based adventure game as our final project! As this was my number one pick, I am very excited and have already started exploring the wide variety of ways we could go about planning and creating our project. This exploration led me a few different places and I learned about some technologies and libraries I was unaware of in the process. To share a couple:

  1. I discovered a cool JavaScript library called jQuery Terminal Emulator for emulating a terminal-like UI in the browser with custom commands.
  2. I learned about creating JSON-RPC services and multiple ways not to integrate one with a Python/Flask application.

And to get some inspiration, I played through a few of my older works of interactive fiction. One game in particular I played through is a demo that I wrote some time ago for a game called The Marble Mansion – and it is the perfect candidate to recreate using the jQuery Terminal Emulator plugin.

The Marble Mansion Demo is the first act for a game I originally made using Inform7, an application for creating interactive fiction. The player wakes up in a decrepit mansion with no memory of how they got there, and the only way to find out (and escape) is to explore the mansion. The game is interacted with by typing commands such as “examine item” or “look at room”. It is a fun game even if it is just a demo (feel free to play it) and the current version works fine, but I would love to recreate it from scratch in order to truly customize the experience (and challenge myself). And after my discoveries, I think I will choose to use JavaScript with the terminal plugin I found in order to rebuild the game in my free time.

Overall, exploring these technologies and my old games was a great exercise in order to get in the correct mindset for planning our capstone project. I already have a lot of ideas for the structure we could follow as well as a few ideas for what the story could be – and I cannot wait to get started!