Interactive Story Engine and Visual Novel Engine
FRISE is a small, MPL 2.0 licensed, Javascript program that let's you write interactive fiction and games directly in HTML -- the format of the World Wide Web.
FRISE games are played in your browser. Games can be hosted on a web site, or can be downloaded and played offline. To play a downloaded game, you just click on the HTML file to launch your browser and start playing!
You write games in your favorite text editor, linking our free interactive story engine script. Choose-Your-Own-Adventure stories are written directly in conforming HTML, without the need to learn a specialized story format language.
More complicated interactions in stories, such as remembering state, are achieved using standard Javascript.
FRISE comes will a small number of useful functions to help you.
An Example Story
Below is the code for an example game. The comments explain the FRISE features being used.
<!doctype html>
<html lang="en">
<head>
<title>An Example Story</title>
<meta charset="UTF-8" >
<link rel="stylesheet" href="frise/css/game.css" >
</head>
<body>
<x-game><!-- Tags beginning with x- are valid HTML, FRISE makes use a small
number of these. The x-game tag goes around the game code. -->
<x-object id="main-character"><!-- Games can have many object's for people,
things, etc., but must have a main-character-->
<x-position>start</x-position><!-- x-position is used to say the location
of an object. The game always presents
the location of the main character.
For other objects, position is optional -->
<x-name>Frise Guy</x-name><!-- name to use when object speaks -->
<x-icon>images/frise_guy.webp</x-icon><!-- icon used if an object speaks -->
<x-smile>Muted</x-smile><!-- Feel free to make up x-tags for other
attributes of your objects -->
</x-object>
<x-location id="start"><!-- An x-location tag is used to define a location -
somewhere an object can be -->
<x-present><!-- x-present tags are used to describe a location when
the main-character is there -->
<h1>The Adventure Begins</h1><!-- Notice how we can use
vanilla HTML in our description -->
<img src="images/fork.webp" alt="A left road and a right road separated by
a giant stainless steel fork -- Made in Dall-E" >
<p>It is a dark and stormy night... You reach a fork in the road.</p>
<x-speaker name="main-character">Whoa! That's a big fork!</x-speaker>
<!-- x-speaker tags can simplify drawing conversations-->
<ul>
<li><a href="#right">Go Right</a></li><!--To create links from one
location to another
url fragments are used. I.e,
#right to go to location right
-->
<li><a href="#change-smile;left">Go Left</a></li><!-- We can also use
fragments to specify actions to
do before going to a location -->
</ul>
</x-present>
<x-action id="change-smile">
obj('main-character').smile = "Brilliant";
/* obj(some_name) is the syntax to refer to the object some_name
loc(some_name) is the syntax to refer to a loc.
x-action tags otherwise contain straight Javascript
Notice in the above we used .smile to refer to the smile property
we had defined with the x-smile tags earlier.
*/
</x-action>
</x-location>
<x-location id="right">
<x-foo>bar</x-foo><!-- Feel free to make up x-tag attributes for
locations too -->
<x-present>
<h1>Victorious!</h1>
<p>You, ${obj('main-character').name},
flash a ${obj('main-character').smile} smile. You win!</p>
<!-- $ {some_expression} is the standard format for Javascript string
interpolation of variables and expressions. FRISE let's you use it in
HTML x-present sections -->
</x-present>
<x-present ck="loc('right').foo == 'bar'" ><!-- the check must be
true for the text below to be presented.-->
Somehow though it felt too easy.
</x-present>
<x-present>
<div><x-button href="#reset;start">Restart</x-button></div><!--
x-button's are another way to make links between locations-->
</x-present>
<x-action id="reset">
game.reset(); // game is the Javascript name for the current game
</x-action>
</x-location>
<x-location id="left">
<x-present>
<h1>The Left Path</h1>
<p>The left path at first seemed very sinister...</p>
</x-present>
<x-present stage="clickProceed('And then...')" ><!-- a link must be clicked
for the below to display -->
<p>And then you, <input data-for="main-character" name="name">,
had a moment of personal growth and
traversing it became easier.</p><!-- Using the data-for attribute
input tags can be bound to values of object properties.
In the case above, the name property of the main-character. -->
<p><a href="#right">Until...</a></p>
</x-present>
<x-default-action>
/*
Default Actions are run for any object or location that has them,
once per turn
*/
if (obj('main-character').position == 'left') {
loc('right').foo = "left";
}
</x-default-action>
</x-location>
</x-game>
<script src="frise/js/game.js" ></script>
</body>
</html>
FRISE has built-in support for a side navigation bar, game save and load buttons, and more. Details about our free interactive story engine can be found in the
Documentation .