Creates a string generator based on a syntax.
{ output : List Tracery.Command.Command
, stack : List Tracery.Command.Command
, next : Maybe Tracery.Command.Command
, constants : Dict String (List Tracery.Command.Command)
, definitions : Dict String Tracery.Syntax.Definition
}
next
- what needs to be generated next?constants
- whatdefinitions
- the grammar rules (see Syntax)fromDefinitions : Dict String Tracery.Syntax.Definition -> Grammar
Turns Definitions into a Grammar.
toString : ({ variable : String } -> String) -> Grammar -> String
Prints the Grammar
generateWhile : (Grammar -> Basics.Bool) -> Strategy -> Grammar -> Random.Generator Grammar
Generates a string while a predicate is valid
import Dict
import Json.Decode
import Random exposing (Generator)
import Result.Extra
import Tracery.Syntax exposing (Definition(..), Expression(..))
import Set
andThenToString : ({ variable : String } -> String) -> Int -> (Grammar -> Generator Grammar) -> Grammar -> String
andThenToString fun seed gen grammar =
Random.step (gen grammar) (Random.initialSeed seed)
|> Tuple.first
|> toString fun
input : Grammar
input =
[ ( "origin", Choose [ [ Value "A ", Variable "animal" ] ] )
, ( "animal"
, Choose
[ [ Value "cat, looking at a ", Variable "animal" ]
, [ Value "bird." ]
]
)
]
|> Dict.fromList
|> fromDefinitions
input
|> andThenToString (\{variable} -> "dog.") 42 (generateWhile (\_ -> True) defaultStrategy)
--> "A cat, looking at a cat, looking at a cat, looking at a cat, looking at a bird."
input
|> andThenToString (\{variable} -> "dog.") 42 (generateWhile (\_ -> True) (noRecursionStrategy (Set.fromList ["animal"])))
--> "A bird."
generateOutput : (Grammar -> Basics.Bool) -> Strategy -> Grammar -> Random.Generator Grammar
Generates an output found in the resulting grammar.
You can use generateCommands
instead, If you intend to get the output right away.
generateNext : Strategy -> Grammar -> Random.Generator Grammar
Computes the command in grammar.next
.
Afterwards the next command gets loaded
import Dict
import Json.Decode
import Random exposing (Generator)
import Result.Extra
import Tracery.Syntax exposing (Definition(..), Expression(..))
andThenToString : ({ variable : String } -> String) -> Int -> (Grammar -> Generator Grammar) -> Grammar -> String
andThenToString fun seed gen grammar =
Random.step (gen grammar) (Random.initialSeed seed)
|> Tuple.first
|> toString fun
input : Grammar
input =
[ ( "origin", Choose [ [ Value "A ", Variable "animal" ] ] )
, ( "animal"
, Choose
[ [ Value "cat, looking at a ", Variable "animal" ]
, [ Value "bird." ]
]
)
]
|> Dict.fromList
|> fromDefinitions
using this function, you can step through the computation
input
|> andThenToString (\{variable} -> "<" ++ variable ++ ">.") 42 (generateNext defaultStrategy)
--> "A <animal>."
The second step does nothing (some steps only perform internal rearrangements)
input
|> andThenToString (\{variable} -> "<" ++ variable ++ ">.") 42
(\g -> g
|> (generateNext defaultStrategy)
|> Random.andThen (generateNext defaultStrategy)
)
--> "A <animal>."
But after a few more steps (and some rewinding), we get the result
input
|> andThenToString (\{variable} -> "dog.") 42
(\g -> g
|> (generateNext defaultStrategy)
|> Random.andThen (generateNext defaultStrategy)
|> Random.andThen (generateNext defaultStrategy)
|> Random.map rewind
|> Random.andThen (generateNext defaultStrategy)
|> Random.andThen (generateNext defaultStrategy)
)
--> "A cat, looking at a dog."
String -> List Tracery.Syntax.Expression -> Basics.Bool
The strategy specifies the algorithm to choose an option
defaultStrategy : String -> List Tracery.Syntax.Expression -> Basics.Bool
This strategy will choose any option
noRecursionStrategy : Set String -> String -> List Tracery.Syntax.Expression -> Basics.Bool
This strategy will never choose a recursive option
onlyRecursionStrategy : Set String -> String -> List Tracery.Syntax.Expression -> Basics.Bool
This strategy will only chose recursive options
toNext : Grammar -> Grammar
Moves to the next command without executing anything.
toNext : Grammar -> Grammar
toNext grammar =
grammar |> withCommands grammar.stack
withCommands : List Tracery.Command.Command -> Grammar -> Grammar
Sets Commands of a Grammar.
skip : Grammar -> Grammar
Puts the current command on the output (without executing it) and then gets the next command.
rewind : Grammar -> Grammar
sets the output as input.
end : Grammar -> Grammar
set the remaining commands as output