The First Three Years of the Twine Cookbook

As this goes out, I’m stepping down as the managing editor of the Twine Cookbook. Can you believe it has been three years since it started!?

As I wrap up my current time with it, I wanted to share more reflections like I did when it celebrated its first anniversary.

Good Twine Pedagogy is Hard

I come from a background of working as an instructional designer and have been creating online educational content for the last nine years. That has included everything from tutorial videos to designing online courses for universities. I’ve worked in a little bit of everything, but something I have spent a large amount of time teaching online is Twine. (I have dozens of videos on versions 1.3.5 through the latest 2.3.)

I include that background because I want to make an important point that has had a huge impact on the design and work behind the Cookbook: Twine has a central pedagogical problem. It’s name is “story formats.”

In Twine 1, story formats were almost entirely layout-related. Using one over another meant changing how different things were arranged or how passages were loaded on the screen. Starting in Twine 2, story formats became not only layout changes, but different scripting languages. Comparing, say, writing code in Harlowe with Snowman shows very different assumptions about how code should be written, understood, and used. Between the now four core story formats, implicit programming styles and structures vary widely. What is relatively easy in one might be impossible in another.

When it comes to teaching how to do things in Twine, this is a nightmare. Each story format requires internalizing how it views passages, the basic unit of Twine stories, and understanding how its different functionality relate to each other. There are some similarities, yes. All of the “scripting languages” are fundamentally based on JavaScript, so they share common data types and control flow structures like conditional statements, but syntactically they are all very different.

Over the years, this has led to increasingly separate communities. They are some users who swear by a particular story format and actively discourage others from using anything else. Some have even invented their own story formats based on one of the core ones. From a development point of view, all of this active work is great! The more people working on a tool and within a coding space, the more its limits can be mapped and even expanded. From a pedagogical view, when trying to document how things work is a central concern? Intensely frustrating! There are people who whose Twine experience with the tool and ecosystem are radically different than others depending on what story formats they use and communities they interact with. This makes trying to teach what it means to “learn Twine” very difficult.

Limitations of Official Documentation

Many people have written code that interacts with story formats in ways that the story format author did not intend. A frequent example concerns Harlowe, the default story format in Twine 2. Many people have discovered what internal events it uses and have created code that listens for and interacts with these events to capture things like passage loading and other things. Some tools have even been developed that use this knowledge to report on user interactions.

The problem comes in when considering what the Harlowe documentation supports. It purposely doesn’t include details on how to edit its internal parts using JavaScript. Nothing is mentioned on how its events work or about its loading of passages. These details can be gleamed from its source code, of course. But an implicit, if not explicit, central design tenet of the story format is to make it as user friendly as possible, and part of that design is locking out using JavaScript directly. For newer users, this is a good choice. For more advanced users, this has meant them exploring and sharing details about how to hack in and use different parts that are not covered in the documentation.

This has also meant, when someone asks for inclusion of certain code or techniques, that they have had to be turned down from being used in the Cookbook. Why? The official documentation of a particular story format doesn’t support using the code in that way! One of the frustrating constraints placed on the Cookbook is that it is Official, capital ‘O’. It has to point at places in story format documentation that explain concepts or where code is referenced. It cannot link to a hack of a story format because that modification is not, itself, Official.

This has also meant that works that use story formats that are not included with Twine 2 have also not been included in the Cookbook. This was not a rule I made, but flows out of the Official nature of the book. If support for that story format disappears after a month or in a year, what happens then? Will those examples be included even if the story format no longer exists? Should the Cookbook support some story formats but not others? The line had to be drawn somewhere and a decision was made to only support those story formats built into Twine 2.

So Many Versions

Looking at the “Change Story Format” modal as part of the Story Menu in Twine 2.3.8 (the current version, as of this writing) shows four story formats: Chapbook, Harlowe, Snowman, and SugarCube.

Chapbook has one branch, 1.X. Harlowe has three: 3.X, 2.X, and 1.X. Snowman has 2.X and 1.X. SugarCube has two: 2.X and 1.X.

This means that there are not really four story formats available in Twine 2.3.8, but eight of them! Each has structural (HTML), syntactical (macros), and functional (global functions) differences. Moving between some pairs is very easy! Others? Impossible! For a long time, for example, Harlowe did not support arrays. Trying to write anything depending on arrays was nearly impossible. SugarCube, as another example, supports using audio files. For a long time, it was the only one that did. (Chapbook also has audio support and brings the total up to half of the build-in story formats.)

How do you communicate to new users that each of these come with their own biases? How do you even communicate that each story format, and its branches, are all different? Should that be something Twine 2 explores or should the Cookbook do that? Where should that explanation be? And how, from starting places of new users, do you explain that there are story formats at all in Twine 2? Nowhere in using the tool does it mention this, what they do, or how they work. There are simply there.

For the Cookbook, this came down to being forced into supporting everything. If a new story format version came out and broke an example, a new one had to be created. If the story format added functionality that made an example easier, a new one had to made and the version noted. Any change from a previous example meant to a new one. And some sets now have multiple examples for story formats where this happened but, like with Harlowe having three branches, they all have to remain in the Cookbook as long as people can use those branches in Twine 2.


I had heavy involvement in developing Twee 3. There was a strong need to document what had become 10 years of an informal format that was supported across multiple tools. Yet, despite nearly a year of hard work within the Twine Committee to create the specification, Twine 2 still does not support Twee. There are (at least) two different story formats that can output Twee, but it is not an input format. Twine 2 only accepts HTML.

The major reason I pushed for a specification of Twee is very simple: HTML is not a human-readable format. Sure, people can parse more complicated HTML structures slowly, but when a Twine 2 HTML file has both its story format and output, this becomes very hard to figure without knowing how all of the pieces work. There needed to be a format where code examples could be shown in the Cookbook. The solution, since it already existed and was used in Twine 1, was Twee. It had been around for years, and currently some people even use it outside of Twine 2 itself. (There is a sizable community of people who only use Twee, in fact, and have developed syntax highlighters for tools like Visual Code and Atom. I’ve even worked on one, myself.)

Using it as part of all the code examples made perfect sense at the time. However, as was quickly pointed out after the first year of the Cookbook, different Twee compilers at the time had their own expectations and syntax. Using it in the Cookbook made for more readable code examples, but there was no clear way to move from the examples straight into Twine 2 without needing to compile the Twee into HTML and then import that new file into Twine 2. Trying to explain which compilers and options to use to achieve this was deemed way too complicated to include or even attempt to explain.

As others who have worked on documentation for tools can tell you, once you start documenting one part of a tool ecosystem, you soon realize other places that need that same level of work. What started as a way to show examples in the Cookbook led to developing the Twee 3 specification and then the Twine 2 story format and HTML output specifications. Working on one meant realizing that there were other places that needed that work. (Once those specifications were out, I wrote a five-part guide to creating Twine 2 story formats based on the new documentation.)

What’s next?

As I write this, I’ve recently read back over and edited an interview I did back in 2017 on Twine for an upcoming book project. (That book should, I’ve been told, finally come out in early 2021). At the time, the Cookbook had just become public and I was talking about how there were plans to include lots of things and that something on the radar for the future was a Twee specification. (Remember, it took nearly a year for that project to finish and months after that for the other two specifications to be finished.)

Toward the end of the interview, I was asked the question that heads this last section of the reflection: “What’s next?” Three years ago, I was excited about the future of the Cookbook and how I was imagining it was a major resource and how I was looking forward to community involvement. Now, years later, I am proud of the work accomplished. As of this writing, it’s over 500 pages long! But, as for community involvement, well, that didn’t really happen as planned.

I spent the first few months of the Cookbook reaching out to people and asking if they would help with the project. Every single person I asked turned me down. I stopped asking for a long time after that. Story format maintainers have contributed things, but the last major contributor to the Cookbook — Hi, Grim! — came after I saw their work and asked if they wanted to contribute. That was two years after the Cookbook had been up and running. It was also the only time someone has agreed to help when I approached them.

I don’t have a good answer for the question of “What’s next?” I mentioned in the interview that it is easier to talk about the past of Twee and Twine than its future. I’ve personally invested a large amount of time in teaching people Twine across its many versions and had, when I wrapped up the 2.0 version of the Cookbook, logged over 250 hours of work in writing and editing. Something like 85% of the Cookbook is my own writing and the rest is content I’ve edited and changed from sources like the Wiki and existing story format documentation.

Given projects like Cradle, I used to think that Twine — via Twee — would eventually move into a good space where people could do narrative design in Twine and export that into other tools as part of a workflow to use with game engines with Unity. I no longer think that. Yarn Spinner, which is heavily inspired by Twee and Sugarcane/SugarCube, solved the story format problem through only having one to deal with when writing code. It also makes the jump from source to using in Unity significantly easier. Like Ink/Inky and its use of the Ink-Unity Integration plugin, they have solved the import/export issue for using an editor with major game engine. Unless Twine 2 accepts Twee as an export and import storage format, I don’t see that ever happening.

There are lots of answers for where Twine 2 might be in the next three years. It could have a complete UI redesign (in the works), have a package manager (something that was proposed last year), or even integrate with the Cookbook in such a way that people can move between examples and their own code smoothly like Inform 7 does. But as for the Cookbook itself? I don’t know. In three years, it grew to 500+ pages. Does that growth continue? I don’t know. Does it shrink back down and lose its Twine 1 content along with the way? I don’t know. I’ve had my turn at the wheel. It’s time to see what others do with the project next.