twee2 0.3.3 → 0.4.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +2 -1
- data/Rakefile +37 -0
- data/bin/twee2 +5 -0
- data/doc/usage.txt +4 -0
- data/lib/twee2.rb +29 -3
- data/lib/twee2/build_config.rb +10 -0
- data/lib/twee2/story_file.rb +10 -1
- data/lib/twee2/story_format.rb +7 -2
- data/lib/twee2/version.rb +1 -1
- data/twee2.gemspec +1 -0
- data/web/.gitignore +15 -0
- data/web/build/CNAME +1 -0
- data/web/build/documentation.html +446 -0
- data/web/build/eg1.html +91 -0
- data/web/build/escape-from-earth.html +94 -0
- data/web/build/escape-from-earth.tw2 +52 -0
- data/web/build/favicon.ico +0 -0
- data/web/build/fonts/glyphicons-halflings-regular.eot +0 -0
- data/web/build/fonts/glyphicons-halflings-regular.svg +288 -0
- data/web/build/fonts/glyphicons-halflings-regular.ttf +0 -0
- data/web/build/fonts/glyphicons-halflings-regular.woff +0 -0
- data/web/build/fonts/glyphicons-halflings-regular.woff2 +0 -0
- data/web/build/images/escape-from-earth.png +0 -0
- data/web/build/images/notepad.png +0 -0
- data/web/build/images/twee2-logo.png +0 -0
- data/web/build/index.html +273 -0
- data/web/build/install.html +162 -0
- data/web/build/javascripts/all.js +15 -0
- data/web/build/javascripts/bootstrap.min.js +8 -0
- data/web/build/javascripts/jquery-2.1.4.min.js +5 -0
- data/web/build/stylesheets/all.css +11 -0
- data/web/build/stylesheets/readable.bootstrap.min.css +11 -0
- data/web/build/tutorial.html +202 -0
- data/web/config.rb +72 -0
- data/web/source/CNAME +1 -0
- data/web/source/documentation.html.haml +411 -0
- data/web/source/eg1.html +91 -0
- data/web/source/escape-from-earth.html +94 -0
- data/web/source/escape-from-earth.tw2 +52 -0
- data/web/source/favicon.ico +0 -0
- data/web/source/fonts/glyphicons-halflings-regular.eot +0 -0
- data/web/source/fonts/glyphicons-halflings-regular.svg +288 -0
- data/web/source/fonts/glyphicons-halflings-regular.ttf +0 -0
- data/web/source/fonts/glyphicons-halflings-regular.woff +0 -0
- data/web/source/fonts/glyphicons-halflings-regular.woff2 +0 -0
- data/web/source/images/escape-from-earth.png +0 -0
- data/web/source/images/notepad.png +0 -0
- data/web/source/images/twee2-logo.png +0 -0
- data/web/source/index.html.haml +184 -0
- data/web/source/install.html.haml +81 -0
- data/web/source/javascripts/all.js +2 -0
- data/web/source/javascripts/bootstrap.min.js +7 -0
- data/web/source/javascripts/jquery-2.1.4.min.js +4 -0
- data/web/source/layouts/layout.haml +54 -0
- data/web/source/stylesheets/all.css +1 -0
- data/web/source/stylesheets/readable.bootstrap.min.css +11 -0
- data/web/source/tutorial.html.haml +119 -0
- metadata +64 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 80fdeb6e878761f0e195156ed16776fdc086b1cf
|
4
|
+
data.tar.gz: 575b4e716c1b2594c9cde614b221403541a759e6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 55b0a31d371fa8cfc7ddb4a96f98d970670aa6080f8eecf929f5f079d5ebac9d5e4b6242b97a23838f632025d208094396c716a6753b810bd6026ce13bcd97ef
|
7
|
+
data.tar.gz: 4e54befc3dac3dcaa6a5d92b318230c590b84a9916847a1abb2887bdde3c13697f05b632d576b56c8c10393f720435bcc108914a911e36135a1143b36c51a082
|
data/.gitignore
CHANGED
data/Rakefile
CHANGED
@@ -1,2 +1,39 @@
|
|
1
1
|
require "bundler/gem_tasks"
|
2
2
|
|
3
|
+
namespace :web do
|
4
|
+
# Yields to a block after chdir'ing to the specified
|
5
|
+
# path (relative to the app root), then chdir's back
|
6
|
+
def run_from_directory(path)
|
7
|
+
old_dir = Dir::pwd
|
8
|
+
Dir::chdir("#{File::dirname(__FILE__)}/#{path}")
|
9
|
+
yield
|
10
|
+
Dir::chdir(old_dir)
|
11
|
+
end
|
12
|
+
|
13
|
+
desc 'Build the website from source'
|
14
|
+
task :build do
|
15
|
+
raise 'Middleman not found. Try "gem install middleman".' if `which middleman` == ''
|
16
|
+
run_from_directory('web') do
|
17
|
+
system("middleman build --clean")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
desc "Preview the website at http://0.0.0.0:4567"
|
22
|
+
task :preview do
|
23
|
+
raise 'Middleman not found. Try "gem install middleman".' if `which middleman` == ''
|
24
|
+
run_from_directory('web') do
|
25
|
+
system("middleman server --bind-address=0.0.0.0")
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
desc "Deploy the website to github pages"
|
30
|
+
task :deploy do
|
31
|
+
run_from_directory('.') do
|
32
|
+
system("git subtree push --prefix web/build origin gh-pages")
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
desc "Build and deploy the website"
|
37
|
+
task :build_dep => [:build, :deploy] do
|
38
|
+
end
|
39
|
+
end
|
data/bin/twee2
CHANGED
@@ -29,6 +29,11 @@ class Twee2CLI < Thor
|
|
29
29
|
Twee2::decompile(url, output)
|
30
30
|
end
|
31
31
|
|
32
|
+
desc 'version', "reports which version you're using and checks what the highest available version is"
|
33
|
+
def version
|
34
|
+
Twee2::version_check
|
35
|
+
end
|
36
|
+
|
32
37
|
desc 'help', 'shows usage instructions'
|
33
38
|
def help
|
34
39
|
Twee2::help
|
data/doc/usage.txt
CHANGED
data/lib/twee2.rb
CHANGED
@@ -12,10 +12,27 @@ module Twee2
|
|
12
12
|
DEFAULT_FORMAT = 'Harlowe'
|
13
13
|
|
14
14
|
def self.build(input, output, options = {})
|
15
|
-
# Read and parse format file
|
16
|
-
build_config.story_format = StoryFormat::new(options[:format])
|
17
15
|
# Read and parse input file
|
18
|
-
|
16
|
+
begin
|
17
|
+
build_config.story_file = StoryFile::new(input)
|
18
|
+
rescue StoryFileNotFoundException
|
19
|
+
puts "ERROR: story file '#{input}' not found."
|
20
|
+
exit
|
21
|
+
end
|
22
|
+
# Read and parse format file, unless already set (by a Twee2::build_config.story_format call in the story file, for example)
|
23
|
+
if !build_config.story_format
|
24
|
+
begin
|
25
|
+
build_config.story_format = StoryFormat::new(options[:format])
|
26
|
+
rescue StoryFormatNotFoundException
|
27
|
+
puts "ERROR: story format '#{options[:format]}' not found."
|
28
|
+
exit
|
29
|
+
end
|
30
|
+
end
|
31
|
+
# Warn if IFID not specified
|
32
|
+
if !build_config.story_ifid_specified
|
33
|
+
puts "NOTICE: You haven't specified your IFID. Consider adding to your code -"
|
34
|
+
puts "::StoryIFID[twee2]\nTwee2::build_config.story_ifid = '#{build_config.story_ifid}'"
|
35
|
+
end
|
19
36
|
# Produce output file
|
20
37
|
File::open(output, 'w') do |out|
|
21
38
|
out.print build_config.story_format.compile
|
@@ -38,6 +55,15 @@ module Twee2
|
|
38
55
|
puts StoryFormat.known_names.join("\n")
|
39
56
|
end
|
40
57
|
|
58
|
+
def self.version_check
|
59
|
+
`gem list -r -q twee2` =~ /\((.*)\)/
|
60
|
+
puts " Your version: #{Twee2::VERSION}"
|
61
|
+
puts " Latest version: #{$1}"
|
62
|
+
if Twee2::VERSION.to_s != $1
|
63
|
+
puts "To upgrade, run: gem install twee2"
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
41
67
|
unless Gem.win_platform?
|
42
68
|
# Reverse-engineers a Twee2/Twine 2 output HTML file into a Twee2 source file
|
43
69
|
def self.decompile(url, output)
|
data/lib/twee2/build_config.rb
CHANGED
@@ -1,14 +1,24 @@
|
|
1
1
|
require 'singleton'
|
2
|
+
require 'securerandom'
|
2
3
|
|
3
4
|
module Twee2
|
4
5
|
class BuildConfig
|
5
6
|
include Singleton
|
6
7
|
|
7
8
|
attr_accessor :story_format, :story_file, :story_name
|
9
|
+
attr_reader :story_ifid, :story_ifid_specified
|
8
10
|
|
9
11
|
# Set defaults
|
10
12
|
def initialize
|
11
13
|
@story_name = 'An unnamed story'
|
14
|
+
@story_ifid, @story_ifid_specified = SecureRandom.uuid, false
|
15
|
+
end
|
16
|
+
|
17
|
+
# Set the IFID - we track when this occurs so that the user can be
|
18
|
+
# nagged for not manually setting it
|
19
|
+
def story_ifid=(value)
|
20
|
+
@story_ifid = value
|
21
|
+
@story_ifid_specified = true
|
12
22
|
end
|
13
23
|
end
|
14
24
|
|
data/lib/twee2/story_file.rb
CHANGED
@@ -1,3 +1,4 @@
|
|
1
|
+
require 'rubygems'
|
1
2
|
require 'haml'
|
2
3
|
require 'coffee_script'
|
3
4
|
require 'sass'
|
@@ -89,7 +90,15 @@ module Twee2
|
|
89
90
|
# Generate XML in Twine 2 format
|
90
91
|
@story_data = Builder::XmlMarkup.new
|
91
92
|
# TODO: what is tw-storydata's "options" attribute for?
|
92
|
-
@story_data.tag!('tw-storydata', {
|
93
|
+
@story_data.tag!('tw-storydata', {
|
94
|
+
name: Twee2::build_config.story_name,
|
95
|
+
startnode: @story_start_pid,
|
96
|
+
creator: 'Twee2',
|
97
|
+
'creator-version' => Twee2::VERSION,
|
98
|
+
ifid: Twee2::build_config.story_ifid,
|
99
|
+
format: '{{STORY_FORMAT}}',
|
100
|
+
options: ''
|
101
|
+
}) do
|
93
102
|
@story_data.style(story_css, role: 'stylesheet', id: 'twine-user-stylesheet', type: 'text/twine-css')
|
94
103
|
@story_data.script(story_js, role: 'script', id: 'twine-user-script', type: 'text/twine-javascript')
|
95
104
|
@passages.each do |k,v|
|
data/lib/twee2/story_format.rb
CHANGED
@@ -6,7 +6,7 @@ module Twee2
|
|
6
6
|
class StoryFormat
|
7
7
|
# Loads the StoryFormat with the specified name
|
8
8
|
def initialize(name)
|
9
|
-
raise(StoryFormatNotFoundException) if !File::exists?(format_file_path = Twee2::buildpath("storyFormats/#{name}/format.js"))
|
9
|
+
raise(StoryFormatNotFoundException) if !File::exists?(format_file_path = Twee2::buildpath("storyFormats/#{name}/format.js")) && !File::exists?(format_file_path = Twee2::buildpath("#{name}/format.js"))
|
10
10
|
@name = name
|
11
11
|
format_file = File::read(format_file_path)
|
12
12
|
format_data = format_file.match(/(["'])source\1 *: *(["']).*?[^\\]\2/)[0]
|
@@ -21,7 +21,12 @@ module Twee2
|
|
21
21
|
|
22
22
|
# Returns an array containing the known StoryFormat names
|
23
23
|
def self.known_names
|
24
|
-
Dir.open(Twee2::buildpath('storyFormats')).to_a.sort.reject{|d|d=~/^\./}.map
|
24
|
+
Dir.open(Twee2::buildpath('storyFormats')).to_a.sort.reject{|d|d=~/^\./}.map do |name|
|
25
|
+
format_file_path = Twee2::buildpath("storyFormats/#{name}/format.js")
|
26
|
+
format_file = File::read(format_file_path)
|
27
|
+
version = format_file.match(/(["'])version\1 *: *(["'])(.*?[^\\])\2/)[3]
|
28
|
+
" * #{name} (#{version})"
|
29
|
+
end
|
25
30
|
end
|
26
31
|
end
|
27
32
|
end
|
data/lib/twee2/version.rb
CHANGED
data/twee2.gemspec
CHANGED
@@ -26,6 +26,7 @@ Gem::Specification.new do |spec|
|
|
26
26
|
spec.required_ruby_version = '~> 2'
|
27
27
|
|
28
28
|
spec.add_development_dependency 'rake', '~> 10'
|
29
|
+
spec.add_development_dependency 'middleman', '>= 3.4.0'
|
29
30
|
|
30
31
|
spec.add_runtime_dependency 'builder', '~> 3.2', '>= 3.2.2'
|
31
32
|
spec.add_runtime_dependency 'bundler', '~> 1.6'
|
data/web/.gitignore
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
# See http://help.github.com/ignore-files/ for more about ignoring files.
|
2
|
+
#
|
3
|
+
# If you find yourself ignoring temporary files generated by your text editor
|
4
|
+
# or operating system, you probably want to add a global ignore instead:
|
5
|
+
# git config --global core.excludesfile ~/.gitignore_global
|
6
|
+
|
7
|
+
# Ignore bundler config
|
8
|
+
/.bundle
|
9
|
+
|
10
|
+
# Ignore cache
|
11
|
+
/.sass-cache
|
12
|
+
/.cache
|
13
|
+
|
14
|
+
# Ignore .DS_store file
|
15
|
+
.DS_Store
|
data/web/build/CNAME
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
twee2.danq.me
|
@@ -0,0 +1,446 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<meta charset='utf-8'>
|
5
|
+
<title>
|
6
|
+
Twee2
|
7
|
+
| Full documentation
|
8
|
+
</title>
|
9
|
+
<meta content='IE=edge' http-equiv='X-UA-Compatible'>
|
10
|
+
<meta content='width=device-width, initial-scale=1' name='viewport'>
|
11
|
+
<link href="/stylesheets/all.css" rel="stylesheet" />
|
12
|
+
<script src="/javascripts/all.js"></script>
|
13
|
+
</head>
|
14
|
+
<body>
|
15
|
+
<div class='navbar navbar-default navbar-static-top'>
|
16
|
+
<div class='container'>
|
17
|
+
<div class='navbar-header'>
|
18
|
+
<a class='navbar-brand' href='./'>Twee2</a>
|
19
|
+
<button class='navbar-toggle' data-target='#navbar-main' data-toggle='collapse' type='button'>
|
20
|
+
<span class='icon-bar'></span>
|
21
|
+
<span class='icon-bar'></span>
|
22
|
+
<span class='icon-bar'></span>
|
23
|
+
</button>
|
24
|
+
</div>
|
25
|
+
<div class='navbar-collapse collapse' id='navbar-main'>
|
26
|
+
<ul class='nav navbar-nav'>
|
27
|
+
<li>
|
28
|
+
<a href='index.html'>Home</a>
|
29
|
+
</li>
|
30
|
+
<li>
|
31
|
+
<a href='install.html'>Install</a>
|
32
|
+
</li>
|
33
|
+
<li>
|
34
|
+
<a href='tutorial.html'>2-minute tutorial</a>
|
35
|
+
</li>
|
36
|
+
<li>
|
37
|
+
<a href='documentation.html'>Documentation</a>
|
38
|
+
</li>
|
39
|
+
<li>
|
40
|
+
<a href='https://github.com/avapoet/twee2'>Source</a>
|
41
|
+
</li>
|
42
|
+
</ul>
|
43
|
+
</div>
|
44
|
+
</div>
|
45
|
+
</div>
|
46
|
+
<div class='container'>
|
47
|
+
<div class='row'>
|
48
|
+
<div class='col-sm-3 col-sm-push-9'>
|
49
|
+
<h2>Index</h2>
|
50
|
+
<ul>
|
51
|
+
<li>
|
52
|
+
<a href='#relationship-to-twine'>Relationship to Twine</a>
|
53
|
+
</li>
|
54
|
+
<li>
|
55
|
+
<a href='#writing-code'>Writing and compiling code</a>
|
56
|
+
</li>
|
57
|
+
<li>
|
58
|
+
<a href='#story-formats'>Understanding story formats</a>
|
59
|
+
</li>
|
60
|
+
<li>
|
61
|
+
<a href='#twee2-syntax'>Twee2 syntax</a>
|
62
|
+
<ul>
|
63
|
+
<li>
|
64
|
+
<a href='#twee2-syntax-passages'>Passages</a>
|
65
|
+
</li>
|
66
|
+
<li>
|
67
|
+
<a href='#twee2-syntax-content'>Content</a>
|
68
|
+
</li>
|
69
|
+
<li>
|
70
|
+
<a href='#twee2-syntax-special-passages'>Special passages</a>
|
71
|
+
</li>
|
72
|
+
</ul>
|
73
|
+
</li>
|
74
|
+
<li>
|
75
|
+
<a href='#includes'>Splitting your code into multiple files</a>
|
76
|
+
</li>
|
77
|
+
<li>
|
78
|
+
<a href='#build-config'>Setting build configuration options</a>
|
79
|
+
</li>
|
80
|
+
<li>
|
81
|
+
<a href='#decompiler'>Decompiling Twine 2 stories</a>
|
82
|
+
</li>
|
83
|
+
</ul>
|
84
|
+
</div>
|
85
|
+
<div class='col-sm-9 col-sm-pull-3'>
|
86
|
+
<h1>Full documentation</h1>
|
87
|
+
<h2 id='relationship-to-twine'>Relationship to Twine</h2>
|
88
|
+
<p>
|
89
|
+
Twee2 is built on top of
|
90
|
+
<a href='http://twinery.org/'>Twine 2</a>,
|
91
|
+
minus the graphical user interface. As a result, virtually all of the
|
92
|
+
<a href='http://twinery.org/wiki/twine2:guide'>documentation about Twine 2</a>
|
93
|
+
(and specifically the documentation about the
|
94
|
+
<a href='http://twinery.org/wiki/twine2:how_to_choose_a_story_format'>different story formats</a>)
|
95
|
+
is relevant to Twee2, too.
|
96
|
+
Because Twee2 is inspired by Twee, its documentation is also a valuable resource: however note that
|
97
|
+
you can't use Twee 'macros' in Twee2.
|
98
|
+
</p>
|
99
|
+
<h2 id='writing-code'>Writing and compiling code</h2>
|
100
|
+
<p>
|
101
|
+
Write Twee2 code using your favourite text editor. Syntax highlighting is available via
|
102
|
+
<a href='https://github.com/monospaced/sublime-twee'>this Sublime Text plugin</a>
|
103
|
+
for Twee. By convention, Twee2 source files have the
|
104
|
+
<code>.tw2</code>
|
105
|
+
extension.
|
106
|
+
</p>
|
107
|
+
<p>
|
108
|
+
Compile Twee2 files using the
|
109
|
+
<code>twee2</code>
|
110
|
+
command-line tool. There are two important modes of operation:
|
111
|
+
</p>
|
112
|
+
<ul>
|
113
|
+
<li>
|
114
|
+
<code>twee2 build input.tw2 output.html</code>
|
115
|
+
produces output.html based on the code in input.tw2
|
116
|
+
</li>
|
117
|
+
<li>
|
118
|
+
<code>twee2 watch input.tw2 output.html</code>
|
119
|
+
does the same thing, but
|
120
|
+
<em>watches</em>
|
121
|
+
input.tw2 for changes, automatically recompiling whenever it is updated (note that it's not
|
122
|
+
smart enough to understand when
|
123
|
+
<a href='#includes'>'included'</a>
|
124
|
+
files have been changed, though).
|
125
|
+
</li>
|
126
|
+
</ul>
|
127
|
+
<p>
|
128
|
+
Because Twee2 source files are just plain text files, they're well-suited to use with
|
129
|
+
source control systems: you could, for example, use
|
130
|
+
<a href='https://github.com/'>Github</a>
|
131
|
+
to share your code or to collaborate with other authors, even working on the same file.
|
132
|
+
</p>
|
133
|
+
<h2 id='story-formats'>Understanding story formats</h2>
|
134
|
+
<p>
|
135
|
+
Twee2 comes with built-in support for all of the same story formats that Twine 2 does:
|
136
|
+
</p>
|
137
|
+
<ul>
|
138
|
+
<li>
|
139
|
+
<a href='http://twine2.neocities.org/'>Harlowe</a>
|
140
|
+
- the default format, which includes a simplified scripting format
|
141
|
+
</li>
|
142
|
+
<li>
|
143
|
+
<a href='https://bitbucket.org/klembot/snowman-2'>Snowman</a>
|
144
|
+
- a minimal format that uses Underscore.js templates and jQuery to provide programmers with a powerful toolset
|
145
|
+
</li>
|
146
|
+
<li>
|
147
|
+
<a href='http://www.motoslave.net/sugarcube/'>SugarCube</a>
|
148
|
+
- a TiddlyWiki-powered format that comes with support for multiple save 'slots' and a Twine 1/Twee 'macro'-like scripting syntax
|
149
|
+
</li>
|
150
|
+
<li>
|
151
|
+
Paperthin - used when you select "View Proofing Copy" in Twine 2, this minimal skeleton isn't really an output format as it is a proofing tool
|
152
|
+
</li>
|
153
|
+
</ul>
|
154
|
+
<p>
|
155
|
+
If you've having difficulty choosing between them, there's
|
156
|
+
<a href='http://twinery.org/wiki/twine2:how_to_choose_a_story_format'>a summary of the differences</a>
|
157
|
+
in the Twine 2 documentation.
|
158
|
+
</p>
|
159
|
+
<p>
|
160
|
+
To specify which format to use during compilation, use the optional
|
161
|
+
<code>--format</code>
|
162
|
+
parameter. E.g. you might type
|
163
|
+
<code>twee2 build input.tw2 output.html --format=Snowman</code>.
|
164
|
+
You can get a list of the formats that Twee2 natively understands by running
|
165
|
+
<code>twee2 formats</code>.
|
166
|
+
</p>
|
167
|
+
<p>
|
168
|
+
It's possible to use any story format, e.g. if you've downloaded or written your own, by specifying the path
|
169
|
+
to the story format's directory (the one containing the format.js file) in your
|
170
|
+
<code>--format</code>
|
171
|
+
parameter. For example, you might run
|
172
|
+
<code>twee2 build input.tw2 output.html --format=./MyFormat</code>.
|
173
|
+
</p>
|
174
|
+
<p>
|
175
|
+
Rather than setting the format on the command-line, it's possible to specify it within your source code
|
176
|
+
itself, using
|
177
|
+
<a href='#build-config'>build configuration</a>
|
178
|
+
options.
|
179
|
+
</p>
|
180
|
+
<h2 id='twee2-syntax'>Twee2 syntax</h2>
|
181
|
+
<p>
|
182
|
+
Twee2 uses a syntax that's heavily inspired-by but not 100% compatible with Twee:
|
183
|
+
</p>
|
184
|
+
<h3 id='twee2-syntax-passages'>Passages</h3>
|
185
|
+
<p>
|
186
|
+
Each block of text in Twee2 exists in a
|
187
|
+
<em>passage</em>.
|
188
|
+
Each passage begins with a title, which is prefixed by two colons:
|
189
|
+
</p>
|
190
|
+
<p>
|
191
|
+
<code>::My Passage Name</code>
|
192
|
+
</p>
|
193
|
+
<p>
|
194
|
+
Passage titles may only contain letters, numbers, basic punctuation, and spaces. Some authors prefer to avoid
|
195
|
+
spaces in their passage titles. Passage titles are not case-sensitive: you don't have to use the same case when
|
196
|
+
referring to a passage every time. Passages titles
|
197
|
+
<em>should</em>
|
198
|
+
be unique within a story: if they're not, only the last passage with a given title will be included in the story.
|
199
|
+
</p>
|
200
|
+
<p>
|
201
|
+
Passage titles may optionally be suffixed by one or both of:
|
202
|
+
</p>
|
203
|
+
<ul>
|
204
|
+
<li>
|
205
|
+
Any number of
|
206
|
+
<em>tags</em>,
|
207
|
+
separated by spaced, inside a pair of square brackets. E.g:
|
208
|
+
<br>
|
209
|
+
<code>::My Passage Name [tagone tagtwo]</code>
|
210
|
+
<br>
|
211
|
+
Tags can be used by code in your story (e.g. to send the player to a randomly-selected passage from a subset).
|
212
|
+
<a href='#twee2-syntax-special-passages'>Some tags have special meanings</a>,
|
213
|
+
as described below.
|
214
|
+
</li>
|
215
|
+
<li>
|
216
|
+
A pair of coordinates, separated by a comma and enclosed within angle brackets. E.g.:
|
217
|
+
<br>
|
218
|
+
<code>::My Passage Name <123,456></code>
|
219
|
+
<br>
|
220
|
+
Coordinates have no meaning to Twee2, but they can be used to enhance compatability with Twine 2: Twine 2 uses
|
221
|
+
these coordinates to decide where to show the passages in its WYSIWYG editor.
|
222
|
+
</li>
|
223
|
+
</ul>
|
224
|
+
<p>
|
225
|
+
If you include both tags and coordinates after a passage, the tags must come before the coordinates, e.g.:
|
226
|
+
</p>
|
227
|
+
<p>
|
228
|
+
<code>::My Passage Name [tagone tagtwo] <123,456></code>
|
229
|
+
</p>
|
230
|
+
<p>
|
231
|
+
Some passages and tags
|
232
|
+
<a href='#twee2-syntax-special-passages'>have special meanings</a>,
|
233
|
+
as described below
|
234
|
+
</p>
|
235
|
+
<h3 id='twee2-syntax-content'>Content</h3>
|
236
|
+
<p>
|
237
|
+
Each passage may contain any amount of content, most of which will be stuff that the player sees. Many
|
238
|
+
story formats understand
|
239
|
+
<em>Markdown</em>
|
240
|
+
formatting in passages, which makes it possible to easily add formatting to your passages. Links to different
|
241
|
+
passages are supported in any of the following syntaxes (where 'Dungeon' is the name of the passage they'll be
|
242
|
+
transported if they click the link, and 'click here', where present, is the text that they'll see to click on):
|
243
|
+
</p>
|
244
|
+
<ul>
|
245
|
+
<li>
|
246
|
+
<code>[Dungeon]</code>
|
247
|
+
</li>
|
248
|
+
<li>
|
249
|
+
<code>[click here->Dungeon]</code>
|
250
|
+
</li>
|
251
|
+
<li>
|
252
|
+
<code>[Dungeon<-click here]</code>
|
253
|
+
</li>
|
254
|
+
<li>
|
255
|
+
<code>[click here|Dungeon]</code>
|
256
|
+
</li>
|
257
|
+
</ul>
|
258
|
+
<h2 id='twee2-syntax-special-passages'>Special passages</h2>
|
259
|
+
<p>
|
260
|
+
Some passage names and tags have special meanings. These are:
|
261
|
+
</p>
|
262
|
+
<h3>::Start</h3>
|
263
|
+
<p>
|
264
|
+
The
|
265
|
+
<code>::Start</code>
|
266
|
+
passage will, by default, be used as the initial passage that your player sees when they start reading.
|
267
|
+
You can override this using
|
268
|
+
<a href='#build-config'>build configuration options</a>,
|
269
|
+
but it's probably easier just to follow this convention.
|
270
|
+
</p>
|
271
|
+
<h3>::StorySubtitle, ::StoryAuthor, ::StoryMenu, and ::StorySettings</h3>
|
272
|
+
<p>
|
273
|
+
These names were used for special passages in Twee 1. They're not used by Twee2, but to maintain compatability
|
274
|
+
with Twee 1 they're ignored and you should avoid using them unless you're writing a story that needs to be
|
275
|
+
capable of being compiled by both Twee 1 and Twee2.
|
276
|
+
</p>
|
277
|
+
<h3>::StoryIncludes</h3>
|
278
|
+
<p>
|
279
|
+
Any
|
280
|
+
<code>::StoryIncludes</code>
|
281
|
+
passages (you can have as many as you like, but you probably should avoid having more than one in any file in
|
282
|
+
order to avoid confusion) are treated as lists of secondary Twee2 files to 'include' into your story. This is
|
283
|
+
described in more detail below, under
|
284
|
+
<a href='#includes'>splitting your code into multiple files</a>.
|
285
|
+
</p>
|
286
|
+
<h3>[stylesheet]</h3>
|
287
|
+
<p>
|
288
|
+
Any passages with the 'stylesheet' tag will not be included in your story, but their contents will be injected
|
289
|
+
into the story's stylesheet. For example, you could write:
|
290
|
+
</p>
|
291
|
+
<p>
|
292
|
+
<pre>::MyCoolStylesheet [stylesheet]

body {
 background: #eee;
}

tw-passage tw-link {
 color: red;
}</pre>
|
293
|
+
</p>
|
294
|
+
<p>
|
295
|
+
It's also possible to use
|
296
|
+
<a href='http://sass-lang.com/'>SASS</a>
|
297
|
+
to enhance your stylesheet. Simply add the tag 'sass' or 'scss' to specify the dialect of SASS that you want
|
298
|
+
to use, e.g.:
|
299
|
+
<pre>::MyCoolStylesheet [scss stylesheet]

body {
 background: #eee;
}

tw-passage {
 tw-link {
 color: red;
 }
}
</pre>
|
300
|
+
</p>
|
301
|
+
<h3>[script]</h3>
|
302
|
+
<p>
|
303
|
+
Any passages with the 'script' tag will not be included in your story, but their contents will be injected
|
304
|
+
into the resulting web page as Javascript. For example, you could write:
|
305
|
+
</p>
|
306
|
+
<p>
|
307
|
+
<pre>::SomeAwesomeCode [script]

alert('This message will appear when the adventure starts!');</pre>
|
308
|
+
</p>
|
309
|
+
<p>
|
310
|
+
It's also possible to use
|
311
|
+
<a href='http://coffeescript.org/'>Coffeescript</a>
|
312
|
+
to make your Javascript development more-beautiful. Simply add the tag 'coffee' to your script block:
|
313
|
+
<pre>::SomeAwesomeCode [coffee script]

alert 'This message will appear when the adventure starts!'
</pre>
|
314
|
+
</p>
|
315
|
+
<h3>[haml]</h3>
|
316
|
+
<p>
|
317
|
+
Put the 'haml' tag into your regular passages in order to allow you to write
|
318
|
+
<a href='http://haml.info/'>HAML</a>
|
319
|
+
code into your passages. HAML is a sophisticated templating language for producing HTML output, and
|
320
|
+
for some it might be preferable to writing plain old Markdown. This includes the ability to inject
|
321
|
+
Javascript/CoffeeScript into particular passages. For example, you could write:
|
322
|
+
</p>
|
323
|
+
<p>
|
324
|
+
<pre>::NicksBar [haml]
%p
 Nick's Bar is exactly the kind of nightspot that helps you remember why you quit drinking.
 A depressed-looking barman pours another beer for an equally depressed-looking drunk, while
 over in the corner a street thug plays with a knife as he eyes you up. The floor is sticky
 and the air reeks of stale alcohol.
%p
 %strong What would you like to do?
%ul
 %li [Nick<-Talk to the bartender]
 %li [BarToilet<-Go to the bathroom]
 %li [BarSit<-Sit in a booth]

:coffeescript
 $ ->
 alert "This message will appear when you reach Nick's Bar!"
</pre>
|
325
|
+
</p>
|
326
|
+
<h3>[twee2]</h3>
|
327
|
+
<p>
|
328
|
+
Passages marked with the 'twee2' tag are not included in your story. However, any Ruby code in them
|
329
|
+
will be executed when the passage is processed by the builder. This can be used to
|
330
|
+
<a href='#build-config'>set build configuration options</a>
|
331
|
+
as described below.
|
332
|
+
</p>
|
333
|
+
<h2 id='includes'>Splitting your code into multiple files</h2>
|
334
|
+
<p>
|
335
|
+
A major benefit of Twee2 over Twine 2 is that it's possible to break apart your story into multiple
|
336
|
+
files, which can be used to structure your work, to facilitate teamworking with or without source
|
337
|
+
control, and to make 'reusable' components such as stylesheets and scripts which can then be injected
|
338
|
+
into later stories. There are two ways to do this:
|
339
|
+
</p>
|
340
|
+
<h3>Using ::StoryIncludes</h3>
|
341
|
+
<p>
|
342
|
+
Insert a
|
343
|
+
<code>::StoryIncludes</code>
|
344
|
+
passage into your file and list within it the names of the files to include. Each will be appended
|
345
|
+
to the end of your story before compilation. For example, the following game skeleton includes the
|
346
|
+
contents of four other files - the main file contains only the
|
347
|
+
<code>::Start</code>
|
348
|
+
passage:
|
349
|
+
</p>
|
350
|
+
<p>
|
351
|
+
<pre>::Start
**Journey To The Centre Of The Earth**

by Dan Q

[Play]

::StoryIncludes
first_section.tw2
second_section.tw2
stylesheet.tw2
javascripts.tw2
</pre>
|
352
|
+
</p>
|
353
|
+
<h3>Using ::@include directives</h3>
|
354
|
+
<p>
|
355
|
+
You can put an
|
356
|
+
<code>::@include</code>
|
357
|
+
directive anywhere in your code to insert the contents of another file at that point.
|
358
|
+
<code>::@include</code>
|
359
|
+
respects your current indentation level (e.g. when using HAML), so it's safe to use at any indentation
|
360
|
+
'depth'. For example, the following passages each include a separate file that contains a description
|
361
|
+
of the house in the distance: that description is shared between the two passages, and updating the
|
362
|
+
file updates the description in both.
|
363
|
+
</p>
|
364
|
+
<p>
|
365
|
+
<pre>::Greenhouse [haml]
%p
 Light shines brightly through the tall glass walls of the ornate wrought-iron greenhouse, and
 the plants are verdant and lively. The [Garden<-door] stands open and a cool breeze blows in.
%p
 ::@include description-of-house.tw2

::Garden [haml]
%p
 The garden winds around decorative trees betwen the [greenhouse] and the [Porch<-mansion].
%p
 ::@include description-of-house.tw2
</pre>
|
366
|
+
</p>
|
367
|
+
<p>
|
368
|
+
Note that neither method of including code works recursively (i.e. you can't include a file that in
|
369
|
+
turn includes another file), but this may be fixed in a future version.
|
370
|
+
</p>
|
371
|
+
<h2 id='build-config'>Setting build configuration options</h2>
|
372
|
+
<p>
|
373
|
+
Creating a passage with the 'twee2' tag can be used to run arbritrary Ruby code or to pass additional
|
374
|
+
options to the Twee2 compiler. This expands the potential capability of Twee2 almost-limitlessly, but for now
|
375
|
+
the only supported options are:
|
376
|
+
</p>
|
377
|
+
<ul>
|
378
|
+
<li>
|
379
|
+
<strong>
|
380
|
+
<code>Twee2::build_config.story_ifid = '<em>[your IFID]</em>'</code>
|
381
|
+
</strong>
|
382
|
+
- used to set the
|
383
|
+
<a href='http://www.ifwiki.org/index.php/IFID'>IFID of your story, to facilitate catologuing. If you</a>
|
384
|
+
don't include this directive, the compiler will suggest a random one to you every time you run it and
|
385
|
+
explain how to add it: if you're going to publish your story publicly, you should add the line it
|
386
|
+
suggests before you do so.
|
387
|
+
</li>
|
388
|
+
<li>
|
389
|
+
<strong>
|
390
|
+
<code>Twee2::build_config.story_format = '<em>[a story format]</em>'</code>
|
391
|
+
</strong>
|
392
|
+
- an alternative way of specifying the story format used by your story, rather than using the --format
|
393
|
+
switch to the compiler. The syntax of format names and means of specifying externally-stored formats is
|
394
|
+
identical to
|
395
|
+
<a href='#story-formats'>using the --format switch</a>.
|
396
|
+
</li>
|
397
|
+
</ul>
|
398
|
+
<p>
|
399
|
+
For example:
|
400
|
+
</p>
|
401
|
+
<p>
|
402
|
+
<pre>::Configuration [twee2]
Twee2::build_config.story_ifid = '41AB7776-D198-40F5-BD54-0493D49DA58C'
Twee2::build_config.story_format = 'Snowman'
</pre>
|
403
|
+
</p>
|
404
|
+
<h2 id='decompiler'>Decompiling Twine 2 stories</h2>
|
405
|
+
<p>
|
406
|
+
It's possible to convert existing (compiled) Twee2/Twine 2 story files, in HTML format, back into
|
407
|
+
Twee2 source files for further editing. This can be used to convert your Twine 2 projects into Twee2
|
408
|
+
files or to easily examine the contents of somebody else's story. This feature does not work on Microsoft
|
409
|
+
Windows. To use it, run:
|
410
|
+
</p>
|
411
|
+
<p>
|
412
|
+
<code>twee2 decompile input.html output.tw2</code>
|
413
|
+
</p>
|
414
|
+
<p>
|
415
|
+
The input HTML file can optionally be a full web URL.
|
416
|
+
</p>
|
417
|
+
</div>
|
418
|
+
</div>
|
419
|
+
<footer>
|
420
|
+
<hr>
|
421
|
+
<div class='row'>
|
422
|
+
<div class='col-lg-12'>
|
423
|
+
<ul class='list-unstyled'>
|
424
|
+
<li class='pull-right'>
|
425
|
+
<a href='#top'>Back to top</a>
|
426
|
+
</li>
|
427
|
+
</ul>
|
428
|
+
<p class='small'>
|
429
|
+
©
|
430
|
+
<a href='https://danq.me/'>Dan Q</a>
|
431
|
+
2015—
|
432
|
+
|
|
433
|
+
Twee2 is distributed
|
434
|
+
<a href='https://github.com/avapoet/twee2'>via Github</a>
|
435
|
+
under the
|
436
|
+
<a href='https://www.gnu.org/licenses/old-licenses/gpl-2.0.en.html'>GNU General Public License version 2</a>
|
437
|
+
|
|
438
|
+
This website is licensed under the
|
439
|
+
<a href='http://opencontent.org/openpub/'>Open Publication License version 1</a>
|
440
|
+
</p>
|
441
|
+
</div>
|
442
|
+
</div>
|
443
|
+
</footer>
|
444
|
+
</div>
|
445
|
+
</body>
|
446
|
+
</html>
|