Ficdown - Writing interactive fiction in Markdown

Being a programmer who enjoys writing in his spare time, I’ve always wanted to give Interactive Fiction a go… the two parts of my brain don’t like to intermingle, though. Every time I’ve sat down at the TADS workbench or Inform 7 IDE I’ve not been able to turn off my programmer switch and get into the actual story creation. It feels too much like programming.

When I write non-interactive fiction I use the awesome site Draft and do everything in Markdown. If you’re not familiar with Markdown, it’s basically a syntax for creating HTML in a much cleaner human-readable format (https://en.wikipedia.org/wiki/Markdown). Some time ago I got the idea that it would be awesome to be able to write interactive fiction the same way… Ficdown is the result.

It’s basically a bunch of conventions added to Markdown that allow you to define a stateful IF game in a file that is itself a valid Markdown file. I’ve done a reasonably detailed write-up and tutorial here:

http://rdsm.ca/ficdown

All of the tutorial examples can be played using the (very alpha-stage) Javascript parser and play engine I wrote up, as well as a slightly longer (but still pretty lame) proof-of-concept game here:

http://if.sitosis.com/robot-king/

If you want to see what the raw Markdown for Robot King looks like, it’s here: http://if.sitosis.com/robot-king/story.md. The javascript parser and play engine runs directly off of that file. I’ve also compiled the source Markdown into HTML if you want to see what that looks like: http://if.sitosis.com/robot-king/story.html (obviously none of the links will work, but it gives an idea of how pleasant and non-programmingish it can feel to build a game in this format).

I know there are already other scripting systems to achieve this kind of game, but I just really, really like Markdown and would prefer to use it instead of learning a different syntax like ChoiceScript. I also like the idea of being able to work on a game at any time over the web instead of being tied to a specific IDE or tool on my PC. It’s also nice to be able to hit a preview button and have the Markdown rendered as HTML–it’s much easier to proof read your scenes, actions, etc when all of the code cruft is removed and you’re just left with your story in a nicely rendered format for reading.

I’d appreciate any feedback or comments. It’s still at the proof-of-concept phase and the idea is quite young.

4 Likes

Interesting. I’ve been experimenting with something similar that uses Markdown, but the resulting scripts aren’t valid Markdown themselves: github.com/textadventures/squiffy

I quite like the idea of using the syntax for headings to define scenes - it’s something I don’t think I’ve got quite right in Squiffy yet, as section/passage definitions are confusingly very similar to links themselves - but what if you didn’t want an actual heading to appear at the top of a scene?

I wonder if the syntax for the “pick up key” example could be easier. Presumably this will be quite a common pattern. Also I’m not sure about redisplaying all the choices each time something like that happens. The way I’d do something like this in Squiffy would be to use the distinction I have between sections and passages - a passage for “pick up key” could set the flag, but all the rest of the choices from the text would still be clickable, so there’s no need to redisplay anything.

A scene that doesn’t display a heading could be defined using an empty anchor title

## [Scene Name]("")

I have thought about way to potentially simplify the pick up key pattern… an obvious way would be to add some kind of shorthand to imply a state as both the conditional and the state toggle in an anchor, so something like

[Pick up key.](?#got-key)

that would automatically hide the link and set the toggle state once its clicked. As for not re-displaying everything once an action occurs, that’s something that could easily be included as an option in the Javascript play engine once it’s a bit more mature. For now I am rendering scenes as they would be rendered in a static-HTML or eBook representation of a story that was pre-compiled from a source file (since that’s one of my goals with Ficdown).

Thanks for pointing me to your Squiffy project, I’ll definitely take a closer look when I have time later today.

I like this approach. I guess my worry (without having tried the thing myself) is that you’d wind up needing more coding functionality than can be stuffed into the link-like syntax.

(When working on choice-based games, I almost always need “if-elseif-elseif-else” constructs. Or sometimes “switch-case” fits the problem better. ChoiceOf games tend to be organized around numeric stats, so you want “x=x+1.5” and so on.)

None of this is mandatory if you’re keeping your design scope limited. What you don’t want is to look back in a year and realize that you’ve invented yet another candy-ass scripting language.

It’s basically what I am doing with txt2tags there: anamnese.online.fr/site2/textall … lue_death/
It’s also possible to write in txt2tags and export to markdown and then to ficdown. Last but not least, txt2tags is very extendable, so you can also write in markdown (and probably use fictown sources) within my system: github.com/farvardin/whatistxt2tags

The limited scope and lack of tacked-on scripting elements such as counters/numerical variables and more complicated conditional statements is definitely by design. I guess the vision I have for the format is to make it easy to write more traditional paperback-CYOA-style stories, but with enough state-tracking built in to allow a user’s actions at any point to have an effect during any later part of the story (as opposed to just deciding what the next scene will be). The ability to move back to scenes you have already read is more of a byproduct of the linking mechanism than something I would expect the type of stories written in this format to use extensively–for example I don’t really think it would be well suited to an Inform/TADS-style “open-world” game, where the player can freely move about a large map, revisiting and interacting with different scenes at their own leisure (though it could be used for such).

The limitation to simple boolean state variables, the lack of ability to toggle them to false once they’ve been set, and limiting conditional checks to conjunctions of positive values only are my attempts to artificially limit the potential scope of games in the hopes that even ones approaching a higher level of complexity could feasibly still be exported to a static hyperlinked format for conversion to stand-alone ebooks. Basically my motivation is that I really enjoy reading CYOA paperbacks with my kids, and would like to write my own that I could play with them on my Kindle, but want the ability to make stories with a little more depth where early decisions can have a longer-term impact later on (without having to manually create different decision-tree-paths for every choice made).

My big worry comes from the fact that, doing the math, with enough states and scenes and complexity it will always be possible to create stories that would simply be too large to be stored in a static format. For example, a hypothetical game with 20 different states and 100 different scenes, in which you could traverse to any of the 100 scenes at any point in the story, and for which the 20 different states could be toggled in any random order; Such a story would have to render each of the 100 scenes over a million times to accommodate each possible state combination (2^20), potentially doubled if each scene also has first-seen text, so that would be 200 million html files or ebook pages. That probably ain’t gonna fit on my Kindle.

My hope is that the specification and its limitations will be enough that writing a story that complex would be a dog to manage and maintain, and instead encourages simpler games. Someone who wanted to write that game should probably be using a different authoring system anyway. A more reasonably written Ficdown game with 100 scenes and 20 state variables where the scenes flow together in a more linear fashion, where certain state combinations can be eliminated due to emergent dependencies between states, and where many of the states are limited to within specific portions of specific decision trees may very well compile to a more reasonable number of static files. I don’t actually know yet, though. I’m not conversant enough in statistical analysis to figure that out… which is why my plan is to finish writing the compiler, write some stories, and see what happens.

1 Like

This does seem quite similar in its goals to Markdown. The one thing it seems to be missing that I’m using as part of the Ficdown spec is the ability to set the title tag on anchors. In Markdown you do this by adding the title in quotes after the href:

[Link text](/link/href "Link title")

I don’t see anything analogous in the Txt2tags syntax.

it’s not in the official txt2tags syntax, but you can use regex to add personnalised markup, so you can do almost whatever your want with it. Another important thing which is missing is my system is the possibility to use flags (State Toggling). I understand some people may need this, for my part I’m more interested in classic CYOA adventures you can export to paper books or ebooks. But I know most ebooks readers have some kind of support for javascript so I guess it could be sensible to make it available one day.

Someone will always be stubborn enough to try. :slight_smile: As long as the processing tool prominently displays the number of generated pages, and you have a notion of what “too many for a Kindle” means, users can self-regulate.

1 Like

This tool looks quite similar to my gamebookformat.

My static output formats (PDF, RTF, static HTML) do not contain any duplicated state sections at all, because I have counters etc that would not work anyway, and I’m assuming anyway that the player of the static version will keep state on eg a paper, like you do for a printed book. I did however think about the possibility of keeping state by duplicating sections, and I have an idea for what naive algorithm I would use to probably bring down the number of duplications if I ever get around to implement it:

Make a directed-graph representation of the story. I guess you have that anyway. Search backwards from every section that has a conditional, and find all paths leading back to a section that sets the conditional (ie search from the locked door back to all sections where a key is found). Then search forward through the story, marking in all sections what state variables can be true, false, or either, in every section in the story. Then a simple iteration over all sections will tell you what sections to duplicate, and for what state variable(s) it has to be duplicated. For instance for the key you only need to consider nodes that are along the paths from finding key to the door(s), and where the player can either have or not have the key (no point in duplicating sections where you are sure the player must have or must not have the key). Of course some sections will still be duplicated multiple times, because several variables could be set or not (and matters) in that location, but it should be much fewer than all of them.

I hope that sounded as easy at it seems in my head. :slight_smile:

1 Like

I finished work on the actual parsing/generation library a few weeks ago. Haven’t had time to do anything else with it for a while. Next step is to turn it into a web or desktop app that can actually be useful to end users.

The approach I took was to create a graph of the story starting at scene 1, then traversing through every possible choice in the game as a player would while keeping track of state, as well as notifying all ancestor nodes in the graph whenever a specific state variable is actually used in a conditional. Processing specific paths in the graph would end at leaf scenes (with no choices) or scene/state combinations that had already been processed elsewhere in the graph. In the end, each node in the graph knows its own current state, as well as which state variables are actually used in future nodes. Once I have that, I go through and “compress” each scene so that they only track the state variables that are actually used in future scenes which generates a new graph with all of the redundant nodes pruned. In my test cases it vastly reduced the number of static files that needed to be generated quite nicely.

I have it generating pretty plain HTML files right now, but adding a templating system and converting those to other formats should be pretty easy. Hopefully in the next few weeks I’ll be able to put out a simple app (hopefully online, but it might be harder since I wrote it in C#) that can actually be used by authors.

Sounds like our tools are or will be quite similar. Your default HTML style looks much prettier though (I really need to do something about my horrible CSS). Also you just keep adding new sections to the page rather than displaying only the current one.

The main difference (except for python vs C#) is probably that you have things like the blockquotes-only-shown-first-time feature that will not really work in a static version? Or are those rendered like your other conditionals so that if you read the EPUB version you will actually have two different versions depending on if you go there the first or second time? Hm, that could be expanded to do something like what the Fabled Lands gamebooks do, where some paragraphs have checkboxes and instructions that “after visiting this n times, go see paragraph mmm instead”. Now that I think about it I have to add that to my todo-list for my own tool (and displaying a quote only the first time is obviously a special case of that).

Yeah, when generating static files I simply treat the first-seen state of scenes with blockquotes as another state variable to keep track of through the rest of the game.

Does anyone in this thread have an interest in joining forces (and efforts) to design a common syntax and perhaps even collaborate a bit on tools?

Like the OP, I’m a developer; as a hobby, I develop games on Android. My last published game was Pirates and Traders. It’s a classical trade/piracy game in the mold of “Elite”, but turn-based, and incorporating a fairly extensive role-playing/interactive fiction/visual novel component. This component is used to create lots of small CYOA snippets, similar to (spoilered image due to size):

Lately, I decided to open up the game to modding and started collaborating with other writers; and suddenly the problem of having a good toolchain arose. How to deal with that… is an issue I’ve been considering for a while.

I’ve already developed an extensive syntax for my games, but to be honest, it’s pretty awful. So that is one of the first things I wanted to change. Changing the syntax alone doesn’t solve the real problem, though (that of making it easy for other people to write stuff). Which is why I started looking into what other people use, and what editors exist.

I love what Inkle studios has done with Inklewriter, and games like Sorcery and 80 days. Unfortunately, their scripting language is JSON-based, which makes it unsuitable for non-technical writers.

I also really like the Choice community, but - unfortunately - not Choicescript. It has approximately the level of complexity that I use in my games, but I’m not a fan of some of the scripting language choices they’ve made.

Using a wiki-style syntax such as Markdown/Markup is something I’ve been thinking of for a while, so pretty cool to see a discussion of that here.

Just from a brief glance, I can see that I have needs/features in my StoryScript, which don’t seem to be well-covered in the proposed Markdown syntaxes I’ve seen this far. I don’t see that this should be a big obstacle to collaboration, though - it’s easy enough to have optional features. This I think could be useful:

  • Agreeing on a markdown syntax, that would be cross-compatible across different implementations.
  • Share experiences and source-code wrt parsing/implementing the syntax across several languages. Perhaps collaborate on various implementations. squiffy is already open-source, which is a good start.
  • Collaborate on a common editing/testing toolchain (and documentation), to make it easy to write stories using markdown.

What do you think, @Rudism, @Alex, @Pelle, @farvadin?

Here’s examples of the sort of syntax I’ve worked with, tweaked to adhere more closely to Markdown (the actual implementation I currently have is more html-like, but the transition is pretty unproblematical).

I let myself be inspired by some of Ficdown’s constructs, which I really liked, and the @ notation from squiffy.

I use $ as a prefix to variables, although I don’t feel that this is ideal (since it is a symbol that may often be used in the text - in my current implementation, I use $$ for the dollar symbol). Can’t think of anything more suitable at the moment, though.

Compared to the other suggestions here, I think the other main difference I have is that I also use hooks into the underlying game engine. Primarily that variables can be objects, and I thus allow dot notation (e.g., $person.name, $person.age), and I have scripting to run stuff in the game engine (@act). Not unlike Alex’s javascript use, I guess.

Thoughts?

I am definitely pro-standardization when multiple efforts are being made to achieve the same ends. In my case specifically, the goals with Ficdown are basically these:

  • Simple syntax that allows authors to focus primarily on writing their story
  • Optimized for generating stand-alone ebooks compatible with any hyperlink-enabled reader

I like the idea of building extensions on top of the base specification that could add, for example, object-oriented variables and scripting functionality (for authors that are willing to invest in learning more complex syntax and trade off portability).

I’m a lazy guy who likes to do things as simply as possible though, so my first impulse would be to forego reinventing the wheel altogether…

Why not just define a way to embed Javascript directly into the story files? The scripting could run natively in any browser or browser-based ereader, and stand-alone apps could include one of the numerous free/open source Javascript engines available. Then efforts could be focused on building a common base-library that would provide necessary tools for interacting with the Markdown-defined story from Javascript (and vice versa). That way you’d be inheriting the power of an already existing and practically ubiquitous scripting language with very little work required in the toolchain.

Twine2 is moving to a markdown based markup. It might be worth joining in with them.

A worthy goal. :slight_smile:

I’m mostly interested in usage in apps, but I’d hope that these goals are not incompatible.

I am wary of such an approach for my use-case, since I allow people to make mods for my games. Currently, I personally vet every mod that anyone suggests (and read through and correct the scripting), which has been easy since there really haven’t been a lot of mods. In future, though, I would like to make it so that people can develop and distribute their own mods without my involvement. Even though Android apps are pretty locked down, giving modders the ability to execute javascript on another persons phone is playing it fast and loose with security (and would likely get the app banned from Google Play). So this is not an option for me.

So for my needs, I’ll need someway to handle this outside of Javascript (which is also more user-friendly; I expect that is why Alex has both options in squiffly).

I plan to try a first implementation of the Ficdown-like markup suggestion I noted above in the coming weeks. I need to do a little work on my current parser, but I expect it should go fine, because the main difference is just the syntax of the markup. What I suggest is pretty much already a superset of Ficdown, so if that goes well, it ought to work with Ficdown as well.

Sounds interesting. Do you know where this is documented? I tried the demo, and checked through the wiki, but I don’t see much about Twine2.

What would be the problem with allowing JavaScript? If it is not allowed to access the internet (and I don’t see an obvious reason it would need to–please correct me if I’m wrong), it can’t really do any harm except through a bug in the program running it, which is a problem with any sort of scripting language.