Cartomancer is a library for interpreting and controlling text with conditional output. It was written in pure C++, with no extraneous dependencies. It’s main use case is games but it’s by no way limited to that environment. You could, just as well use it to determine text that needs to change according to application configuration or environment.
Cartomancer is open source and available here
Project Status
Cartomancer is still under development. Currently (1.0) there is still some code cleanup I want to do, and some additional features and fixes I want to implement. If you want to know more or ask for a specific thing, feel free to let me know, I’d be super excited to know people to actually be using this
To me Cartomancer is a “standard priority” project and has to share my time with all of the other things I’m juggling, so no promises on when the next version is out. Check out at the end for version history and known issues.
What is "conditional text"
Cartomancer parses plain text string which have inlined “conditional statements”. These statements are always tied to a controlling variable and the actual displayed text will depend on the value of said variable.
One of those strings might look like this:[ myVar | this is shown if myVar is true| and this if it’s false].
Unconditional strings, these statements can represent one of three types of text elements: Substitutionconditions just insert the current string value of the condition wherever they’re declaredCurrently using [app.CacheSizeMb] of RAM
Switchconditions, like the first example, compare the condition variable to a predetermined set of discrete values and chooses the appropriate output from a set. For boolean type switches, an empty string can be left implied for a “false” valueMuch the same as you, [npc.Pronouns|he|she|they] looked about to break out in tears of joy.
Rangeconditions compare the condition variable, as a float, to a series of thresholds. You can configure both minimum and maximum values for those thresholds[rangeVar 5 10 15| rangeVar is between 5 and 9.9 | rangeVar is between 10 and 14.9 | rangeVar is 15 or higher]
Syntax
Cartomancer treats the input text as UTF-8. The examples above all show the default settings but the separators and delimiters are all configurable depending on your own needs. The elements below are all potentially valid configurations
{somevar,10,15,13;text1;text2}
😎myVar[split_here]someText😋
Please consult the config header for more information
How it works
[var1| [var2| var1 is true and var2 is true| var1 is true and var2 is false] | var1 is false (var2 not relevant)]Each
Text object has a vector of potential outcomes and is attached to a Condition. The Condition itself holds the type of the text/condition pair. If the Condition is
a Range, then the Text holds what thresholds it will respond to. If one or more branches in the Text have conditions internal to them, their text content is replaced with a special placeholder marker and a child Text is created. Text for it’s content. It then verifies the value of its Condition and chooses it’s output accordingly. If that output would contain the output of a child, it asks for that output and assembles the final text accordingly. The
Conditions and Configuration are kept in a Context object. Text and Condition consult this context for information on how they should be constructed. The Conditions are stored as a set, this means that every Text that refers to a particular myVar will all refer to the same Condition object. In order to update the variables, you get it from the Context and upon doing so and requesting a text content update, all instances will recalculate their output. Though the
Context behaves, at first glance, like a singleton, it is not one, code-wise and you can have multiple of them if you want. This is required if you want to have different copies of the same variable with different values. As of Cartomancer 1.0, there is no way to process a Text element using a different Context than the one it was created with, so you would have to have a copy of that as well. Further Information
For information on building Cartomancer, please refer to the repository documentation.
For an example of how to use it, you can check out Foreteller, an application built
with Cartomancer at its core.
Foreteller is built with Qt and wraps the Cartomancer types in QObject elements
so it can forward them to its QML UI.
Version
1.0 (initial release)
Known Issues
- Cartomancer does not handle some mismatched conditions correctly. Make sure you
have a consistent number of alternatives for your switch conditions. Should be fixed in 1.1
Version history and Change log
Initial release