Project: Fantasy Name Generator (Part 1)

For my first post of actual content, I thought I’d write about a recent small C++ project I took on.

For a bit of background, I play a lot of fantasy RPGs.  The identity of my characters is very important to me — not always from a roleplaying perspective (though sometimes that too), but more the combination of name and appearance.  I spend a lot of time in character generation honing those two aspects.  I’ve gotten booted out of games for “inactivity” timeouts because they didn’t feel that character generation counted as doing things.

This project dealt specifically with names.  I have a decent sized stable of names which I’m fond of and use frequently, but sometimes for one reason or another, that option isn’t available to me and I get to think up new names.  Usually this involves thinking of names I’ve liked in the past, combining, swapping vowels, reordering syllables, and just generally playing with letters like Lego bricks until I come up with something that’s both aesthetically appealing, and available for my use in the game in question.

One recent time in particular, I wanted to move away from my long-held personal quirk of using names beginning in K, so that invalidated my entire stable of regulars and necessitated that I do a lot of name mangling.  To get some name seeds to play with, I ended up using some online name generator websites.  Most work pretty well, but every now and again I’d run across one and just scratch my head going “Man, I could write a better namegen than that.”

Famous last words.

The final straw was a “syllable-based” generator which had… well, let’s just say some very interesting definitions of what constituted a syllable.  Seeing systems which work according to non-intuitive rules is always good to make me start pondering the nature of those rules, and figuring out sets of rules to procedurally generate results that are more in line with how I think things should work.

(My vocalization of this mental process, to an outside observer, may have sounded a lot more like “Man, I could write better syllable logic in thirty seconds, and better syllable code in ten minutes.”)

Here is the logic I ended up with, taken directly from a comment within my code:

/*
A syllable can be any one of the following:  A vowel sound, a consonant
followed by a vowel, a vowel followed by a consonant, or a consonant-
vowel-consonant.  Vowel sounds can be individual vowels or two-vowel
combinations.  Consonants can be a single consonant or one of a list of
pre-defined consonant pairs, divided between beginning and end -- "br"
is good for beginning but not end; "tt" or "st" is good for an end but
not a beginning, where "sh" is good for either.

If one syllable ends in a consonant, then the next syllable must begin
with a vowel.  If a  syllable ends in a vowel, then the next syllable
must begin either with a consonant, or with an apostrophe indicating a
glottal stop.
*/

I ended up later removing the glottal stop apostrophe, because while apostrophes in fantasy names can be very well done, they can also be very overdone.  Also, there’s a very practical factor in that a lot of games don’t support arbitrary apostrophes.

So the next step was to create symbols representing each syllable:

/*
Valid sound patterns:
A          -- single vowel
E          -- two-vowel (oo, oe, au, ei, etc.)
B          -- single consonant
Bb         -- Beginning-of-the-syllable consonant pairs
bB         -- End-of-the-syllable consonant pairs
*/

I used E rather than AA for a two-vowel pattern because it seemed to me that AA could just as well represent two one-vowel patterns.  I found it easier to use Bb and bB to represent beginning/end consonant pairs than C and D, though.  Go figure.

Having tokenized my list of valid sound patterns, time to start putting them together into actual syllables.

Valid syllable patterns:
A  E  BA  BE  AB  EB  BAB  BEB  BbA  BbE  AbB  EbB  BbAB  BbEB  BABb 
BEBb  BbAbB  BBeBB
Eliminated several of these in the actual code below because 5- and 
6-character syllables tended to produce long, complicated names that
weren't very appealing, like "ucuinbhaigawn " and "pheumpaukhoev"

Those were actual names generated, by the way.

That’s pretty much the core of the basic namegen logic.  I’ll leave it for a future post to dig further into the details of the logic, and into the code.

Leave a comment