Read about our upcoming Code of Conduct on this issue

  1. 31 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Removed Section.updateEnchantments(), as it doesn't actually work as intended. · 02cfd0e36eae
      Leon Arnott authored
      Section.updateEnchantments() was designed to keep all the enchantments in a section up-to-date even in the face of nebulous DOM manipulations to the passage. However, it turns out that few situations rely on it, and its presence caused some bugs where multiple enchantments refer to the same hook or text. So, I'm trying to go on without it.
      Also fixed a bug where the header syntax didn't work on the first line of a passage.
  2. 29 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Altered "is", "is in" and "contains" to use compare-by-value. · 90f6b08800bc
      Leon Arnott authored
      Now, instead of using JS's compare-by-reference semantics, TwineScript compares containers by value - that is, by checking if their contents are identical. This brings them into alignment with the copy-by-value semantics used by (set:) and such.
  3. 28 Dec, 2014 1 commit
  4. 26 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Fixed a bug where (else-if:) didn't work correctly with successive (else:)s. · 7ef3970bfcc7
      Leon Arnott authored
       * If an (else-if:) followed an (if:) that had been true, then it would cause any other (else:) macros following it to be true as well, due to resetting the section's lastHookShown flag. This is now fixed, albeit in an uncomfortable special-case manner.
       * Also fixed a bug where <tw-expression>s' js attrs were incorrectly being unescaped twice, thus causing macro invocations with "<" symbols in it to break.
       * New error: you can no longer attach non-positional expando properties to arrays using property syntax (e.g. (set: $a's Garply to "grault")).
  5. 25 Dec, 2014 2 commits
    • Leon Arnott's avatar
      Bumped the format.js version to 1.0.1. · 745f01896bff
      Leon Arnott authored
    • Leon Arnott's avatar
      Added the ability to property-reference arbitrary values, not just variables. · 1d6703a6efc4
      Leon Arnott authored
      This means that you can now use "(history:)'s last", or ""Red"'s 1st" as expressions, without having to put the entity in a variable first.
      One consequence: I've eliminated the ability to use property reference outside of macros - you can no longer do $var's 1st, etc. in plain passage text, without wrapping a (print:) around it. On reflection, it simply feels too hard to distinguish amidst normal prose without that wrapper.
      Other bugfixes:
       * Fixed (reload:) and (gotoURL:), which previously errored regardless of input.
       * Fixed bugs introduced in previous commits regarding text nodes as alternatives to charspans. Specifically: PseudoHookSet.forEach() didn't work well when the pseudo-hook had multiple targets; Utils.transitionIn() and other methods couldn't transition text nodes correctly.
       * Fixed a bug where assigning from a hookset to a variable, such as (set: $r to ?l), didn't work right.
  6. 22 Dec, 2014 2 commits
  7. 21 Dec, 2014 2 commits
    • Leon Arnott's avatar
      Fixed a bug preventing pseudo-hooks (strings) being used with macros like (click:). · 6dc2272b7152
      Leon Arnott authored
      The bug prevented the author from, for instance, writing (click: "text") to apply a click macro to every instance of the given text.
      Also, an addendum to the previous commit: the story stylesheet and Javascript should now be functioning again.
    • Leon Arnott's avatar
      Fixed two bugs, eliminating charspans as a result. · d214756b26d0
      Leon Arnott authored
       * Decided that the charspan method of pseudo-hook selection was too fraught with problems (in particular, problems with Bidi or RTL text such as Arabic) so I've replaced it with a new TextNode slicing system. Now, the <tw-pseudo-hook> elements are created around TextNodes which are sliced out of existing nodes, then reinserted afterward. While the departure of charspans means that charspan-selecting CSS is no longer available, I hope I can provide a solution for that at some future point.
       * Fixed a bug where (display:)ed passage code wasn't unescaped from its HTML source.
  8. 19 Dec, 2014 1 commit
  9. 15 Dec, 2014 2 commits
    • Leon Arnott's avatar
      Removed (cloak:), (uncloak:), (css:), (remove:), (nobr:) · 9af692c8d344
      Leon Arnott authored
      (remove:) is one whose name I'm not keen on, and I've decided to remove it in place of the (replace:)[] idiom. (css:) is not a recommended use-case and can be accomplished with HTML, (nobr:) is fulfilled by the curly-brace syntax, and (cloak:) and (uncloak:) currently don't work too well with the rendering flow of sections. Maybe those will return in the future, but they're not too usable for 1.0.
    • Leon Arnott's avatar
      Added an error message for using Twine 1 macro syntax. · 3728a666e3e9
      Leon Arnott authored
      Also, I've reinstated the | separator as an alternative right-separator for the link syntax, albeit as an officially deprecated feature.
  10. 14 Dec, 2014 3 commits
    • Leon Arnott's avatar
      Removed State saving and loading code, and the LZString dependency, for now. · 446a3cbc3d07
      Leon Arnott authored
      For 1.0, game state saving is unavailable, due to the difficulty of saving the variable state for such a diverse range of TwineScript object types. Hopefully it will return soon.
      This also comments out the development-only REPL module usage, too.
    • Leon Arnott's avatar
      Added necessary (count:), (subarray:) and (substring:) macros for collections. · 8ec48a428253
      Leon Arnott authored
      (count:) yields the number of occurences of an item in a collection. (subarray:) and (substring:) are essentially semantic wrappers above the .slice methods of these JS entities. These three macros allow, among other things, manipulation of the (history:) array, and arrays in general, to be less of an ordeal.
    • Leon Arnott's avatar
      Removed (visited:), (previous:) and (turns:), replacing them with (history:). · 5cdf545b6505
      Leon Arnott authored
       * Moved various macros pertaining to collections into a "datastructures" module within the macrolib directory.
       * Moved various utility functions pertaining to TwineScript into an "operationutils" module.
       * The (history:) macro simply returns the State.pastPassageNames array, a non-unique array of passage names in order of visitation. The preceding macros can be emulated by using the "contains" operator and accessing the "length" property of this array.
       * Moved utils.js out of the utils folder, for consistency with other such folders.
       * Added another test file for dataset.
       * Deleted the /lib subfolder, which I'd meant to do in a previous commit.
  11. 13 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Replaced (event:) with a more general (stop:) command used within (live:). · d1e72bb0a2ff
      Leon Arnott authored
      After some reflection I've concluded that the distinction between (event:) and (live:) is a bit too high-level and ill-distinguished. I prefer having just a single "live" macro, (live:), rather than two with subtly different (and crumbily-defined) behaviour. So, I've fallen back to an alternative I had in mind: a (stop:) command which, when appearing inside a live hook, stops the nearest (live:) from repeating. This is more verbose, of course, and I don't quite like the look of it, but it's what is called for.
      Also: fixed a bug where anonymous hooks couldn't appear just before HTML tags. (This caused certain macros, such as (background:), to break indirectly.)
  12. 11 Dec, 2014 1 commit
  13. 10 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Added the (event:) macro, as promised. · fd47c99012b0
      Leon Arnott authored
      (event:) is in essence a (live:) macro that ceases to re-run once some text first appears inside the attached hook. It's designed to be used alongside (if:) and (else-if:), and fulfills the functionality that (when:) used to have.
  14. 09 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Replaced the sensor macros with the (live:) macro. · 1971e8869fbb
      Leon Arnott authored
      This macro, as I may've hinted before, simplifies the evaluation model of Twine 2 macros, eliminating the special case that sensors had. Rather than its expressions being stored in a thunk, they are now evaluated eagerly as normal, and now rely on the enclosing hook's (if:) macros to provide the conditional. In essence: (whenever: $g is true)[Bananas] becomes (live:20ms)[(if: $g is true)[Bananas]]. There is, of course, an increased verbosity to this syntax, but its simplified conceptual model, and composability with other macros, provides a greater boon.
      (But, this macro isn't yet sufficient to replicate (when:), at least without clunky signalling temp variables. The next commit will add an (event:) macro which brings (when:)'s one-time behaviour to the scene.)
      I've removed all occurrences of thunks in the code - now, all macros receive their arguments as bare values, which incidentally brings a slight performance gain.
       * Updated several test files' code.
       * Changed the (if:) macro so that its default transition is "instant" - this allows greater composition with (live:), and also fixes some transition quirks associated with it.
  15. 06 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Added (datamap:) and (dataset:), wrappers for the ES6 Maps and Sets. · 38b6d339323a
      Leon Arnott authored
       * Datamaps are ES6 Maps, safer versions of JS objects with a cleaner keyspace. They're the intended associative array type for Twine 2. (One concern, though, is that currently there's no means of setting an object in key position, let alone accessing said key's value later - hence defeating its primary advantage over using a null-object instead.)
       * Datasets are plain Sets - unordered collections with a uniqueness constraint. Spread syntax works with them, so it's easy to convert an array to a dataset and back. Incidentally, the "data" prefix is to help distinguish their names as nouns - "map" and especially "set" are common verbs.
       * Changed the syntax for property access from "." to "'s" - that is, you write "$array's 1st" instead of "$array.1st". This was a long time coming, but I didn't feel the need to pull the lever until Map property access was needed.
       * Also added "2nd-last" property sugar for array access - "$array's 2nd-last" maps to the Javascript "array[array.length-2]".
       * In order to access ES6 Map and Set, es6-shim was included as a dependency. While adding this, the lib folder and its ad-hoc collection of libraries was removed - the libs are now accessed from node_modules.
  16. 05 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Reorganised the SCSS a bit. · c611ec7573f4
      Leon Arnott authored
       * Renamed style.scss to main.scss, and reorganised the selectors in order of the Twine element hierarchy.
       * Also, I've given all elements box-sizing:border-box and position:relative by default, as these are more desirable alternatives to their defaults for general styling.
       * Moved the link and enchantment styles to a new file, links.scss.
       * Changed the brace style in the other files.
       * Gruntfile: reordered the tasks so that the heaviest task (requirejs) is now last.
  17. 03 Dec, 2014 1 commit
  18. 01 Dec, 2014 1 commit
    • Leon Arnott's avatar
      Fixed bugs for string literals and passage names containing quotes. · e1cc07faa5f9
      Leon Arnott authored
       * Now, string literals can be denoted with any number of " and ' marks, similar to how the verbatim syntax works.
       * Important change: empty strings can no longer be created syntactically - you must use (text:) with no arguments. This is a bit unexpected, but it comes with the advantage that it is a bit more explicit.
       * The backtick is no longer used to denote a string literal. Previously, it had been used as an alternative that allowed both " and ' to coexist in the same string. However, the above changes make this no longer necessary, and its continued presence was confusing given the
       * Also fixed a bug where passageName would fail for passages whose names contained " marks.
       * Additionally, updated the ES6 shims to rename String.prototype.contains to String.prototype.includes, as per the current ES6 specification.
       * Finally, fixed a TwineMarkup bug where decimal numbers weren't being correctly recognised.
  19. 30 Nov, 2014 1 commit
    • Leon Arnott's avatar
      The link syntax now desugars into (link-goto:) calls. · 0e066d4121ec
      Leon Arnott authored
      Renderer now converts twineLink tokens into link-goto syntax instead of generating <tw-link> HTML directly.
      There are a few bugs: passage names with "-marks and `-marks in them don't work yet, but these fixes are forthcoming. Also, debug mode will now display all links as (link-goto:) calls, which isn't ideal and will hopefully be changed shortly.
  20. 29 Nov, 2014 2 commits
    • Leon Arnott's avatar
      Removed trailing whitespace from various lines. · d4546c785351
      Leon Arnott authored
    • Leon Arnott's avatar
      Added ES6 spread syntax to macro calls. · 92e60a92aa41
      Leon Arnott authored
      By putting the ellipsis "..." operator before an array or string, the elements are changed to positional elements in the macro call, separated by  commas. Hence, (print: ...(a: 2, 4)) is the same as (print: 2, 4). It's standard JavaScript ES6, but it's implemented in ES5 for maximum browser support. I considered briefly the "*" splat symbol used by Ruby and Python, but decided that it clashed with the variable sigil ("*$var" looks unsightly).
      Given the existence of spread, the (any-of:) macro is no longer needed.
      Also: added a (range:) macro which, like its Python equivalent, creates an integer range array. I wanted to add range literal syntax, but I've decided I'm perhaps jumping the gun on literals at the moment, and should take it slow.
  21. 27 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Formally implemented (link-goto:). · 406730e10c41
      Leon Arnott authored
      (link-goto:) is a command macro that produces a passage link, essentially an eager-argument version of (link:…)[(goto:…)]. The future goal is for the link syntax to desugar into this macro, as I mentioned earlier, and also to allow (transition:) commands to be attached to this. But, at the moment, it acts as a convenient link macro by itself.
      Also: altered Colour.create so that it can now accept a CSS3 colour name, and correctly use jQuery#css to convert it to an RGB object. However, this is currently not used anywhere, so it may prove to be extraneous.
  22. 23 Nov, 2014 2 commits
    • Leon Arnott's avatar
      Added some more test HTML files. · 8c08c662f38b
      Leon Arnott authored
      Also fixed a bug in the previous commit.
    • Leon Arnott's avatar
      Added preliminary whitespace-collapsing markup braces. · 77f696be93eb
      Leon Arnott authored
      The { and } braces now denote passage prose whose whitespace must be collapsed - runs of \s and \n are converted to a single space, thus eliminating whitespace.
      This implementation has two deficiencies so far: the syntax does not nest, and it affects string literals inside macro tags. Both of these need to be addressed at some point.
      Also: renamed the internal ChangeDescriptor 'cloaked' property to 'enabled', and inverted it.
  23. 22 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Fixed some major ChangerDescriptor bugs introduced recently. · 18d78668a122
      Leon Arnott authored
      The bugs prevented interaction changers like (click:) from hiding their attached hooks.
       * Added two more assert functions to Utils, assertMustHave() and assertOnlyHas(), which confirm that the properties of received objects match a given list. They're ad-hoc object shape-checking, one of JS's known native deficiencies. Whether or not I add these to other methods is up to me.
       * Corrected a typo in one of the test files' names.
  24. 20 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Implemented passage name expressions in links. · 630e9598abc8
      Leon Arnott authored
      Now, similarly to Twine 1, links may have expressions in passage name position, which are used to determine the passage to go to. But! These are slightly different to Twine 1's "try to read as JS, fallback to bare text" method - instead, it is interpreted as TwineMarkup, and the text content that results is used as the passage name.
      I believe this fits with people's preconceptions - [[**Passage**]] is bold text that links to "Passage", and [[Link->$var]] uses $var as the name, even though it's not in a TwineScript context.
      Also, I decided to recant on the tailedLink production in TwineMarkup.
  25. 18 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Various fixes related to macro calls. · 5ae8f7cf4770
      Leon Arnott authored
       * Warnings are now hidden outside of debug mode, as intended.
       * Temporarily fixed passage transitions (in the interim before a means of specifying transitions to (goto:) is implemented).
       * Fixed bugs where the call signature of ChangerCommand.create() was wrong.
       * Now, a multi-name macro will be referred to by its 1-name in type error messages, rather than just "the macro". This means it will sometimes not match the actual name the author used, but will still provide some information.
       * Laid internal groundwork for Twine 1.4-style extensions to the link syntax.
       * Fixed (goto:) calling the wrong Story method, again.
  26. 17 Nov, 2014 1 commit
  27. 16 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Partially implemented a (link:) macro. · 962facd301a2
      Leon Arnott authored
      The point of this macro is to A) provide a more convenient means of immediately making single links that do things, rather than writing a hook and the (click:) macro, and B) to eventually host passage links, via the link syntax desugaring to a (link-goto:) call. This would potentially allow transitions, (set:) macros, etc. to be more easily attached to links, in a less bespoke fashion than in Twine 1. But, it's not quite done yet.
       * Remembered to update the Gruntfile with the recent folder hierarchy changes.
       * Refactored renderError() within Section, thus allowing sensor macros to generate proper error HTML.
       * Fixed a bug where onlyNumbers() in Operations wouldn't properly propagate errors passed into it.
  28. 15 Nov, 2014 2 commits
    • Leon Arnott's avatar
      Fixed some bugs in the previous commit. · db51643650d3
      Leon Arnott authored
      Also completed the renaming of JS files to an all-lowercase standard.
    • Leon Arnott's avatar
      Made (print:) into an explicit command, distinct from (text:) · 7adf822f81d0
      Leon Arnott authored
       * (print:) now emits a PrintCommand, which is an object that prints the expression when it hits the passage. This difference aligns its name (the imperative verb "print") with its implementation.
       * Command-emitting macros are now in a macrolib/Commands module. These currently include just (display:), (goto:) and (print:).
       * Author-facing datatypes now use the TwineScript_Print() function to determine their printable form, not toString(). This eliminates a special case in Section that HookSets used, and also allows (goto:) to behave better.
       * Operation: Moved toJSLiteral() from a private method to a Utils method.
       * Markup: Converted the four inequality tokens "lt", "gt" etc. into one "inequality" token.
       * Fixed a final bug regarding ChangerCommand's file movement.
  29. 12 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Moved internal types to an internaltypes folder. · f84f16e4df63
      Leon Arnott authored
      It was getting confusing having the author-facing types and the non-exposed types in the same category.
      Also fixed a bug where the "[changer] macro should be assigned" warning was being suppressed, and another bug where the enchantment macros were broken.
  30. 11 Nov, 2014 1 commit
    • Leon Arnott's avatar
      Changed the implementation of ChangerCommands from JS functions to objects. · d4a5e999895c
      Leon Arnott authored
      There wasn't really a compelling reason to make ChangerCommands happen to be JS functions - if anything, it made them jolly hard to serialise, and made composing them a scant bit inefficient.
       * (set:) now passes objects by value, cloning them instead of assigning them. This was a long-sighted goal of mine - the difference between pass-by-reference and pass-by-value was always a confusion fount for new users. If (let's be honest, when) we'll need it again, I think I'll add an explicit (alias:) macro that does pass-by-reference (and fails for primitives).
       * Added some more TwineScript datatype internal methods: TwineScript_+ is used for overloading + (currently only used by ChangerCommands and Colours) and TwineScript_Clone is used by (set:) for cloning.
      I should mention that this is a somewhat volatile commit, owing to the two changes above.
  31. 10 Nov, 2014 1 commit
    • Leon Arnott's avatar
      (else:) and (elseif:) now work with non-(if:) boolean expressions. · 9c7f10065553
      Leon Arnott authored
      Now, if an (else:)/(elseif:) follows after a hook that was hidden by any boolean expression, then it should behave as expected, even if said expression wasn't necessarily an (if:), (unless:) or (elseif:).
       * Fixed (else:)'s type signature.
       * Tentatively added (visit:), which is a boolean value macro that returns true if it's the nth visit to the passage (where n is the sole parameter).